// SPDX-License-Identifier: GPL-2.0
/* Copyright (C) 2019 Intel Corporation */

#include <linux/gpio/driver.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/of_address.h>
#include <linux/of_irq.h>
#include <linux/pinctrl/pinctrl.h>
#include <linux/pinctrl/pinconf.h>
#include <linux/pinctrl/pinconf-generic.h>
#include <linux/pinctrl/pinmux.h>
#include <linux/platform_device.h>
#include <linux/property.h>

#include "core.h"
#include "pinconf.h"
#include "pinmux.h"
#include "pinctrl-equilibrium.h"

#define PIN_NAME_FMT	"io-%d"
#define PIN_NAME_LEN	10
#define PAD_REG_OFF	0x100

static void eqbr_gpio_disable_irq(struct irq_data *d)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
	struct eqbr_gpio_ctrl *gctrl = gpiochip_get_data(gc);
	unsigned int offset = irqd_to_hwirq(d);
	unsigned long flags;

	raw_spin_lock_irqsave(&gctrl->lock, flags);
	writel(BIT(offset), gctrl->membase + GPIO_IRNENCLR);
	raw_spin_unlock_irqrestore(&gctrl->lock, flags);
	gpiochip_disable_irq(gc, offset);
}

static void eqbr_gpio_enable_irq(struct irq_data *d)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
	struct eqbr_gpio_ctrl *gctrl = gpiochip_get_data(gc);
	unsigned int offset = irqd_to_hwirq(d);
	unsigned long flags;

	gc->direction_input(gc, offset);
	gpiochip_enable_irq(gc, offset);
	raw_spin_lock_irqsave(&gctrl->lock, flags);
	writel(BIT(offset), gctrl->membase + GPIO_IRNRNSET);
	raw_spin_unlock_irqrestore(&gctrl->lock, flags);
}

static void eqbr_gpio_ack_irq(struct irq_data *d)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
	struct eqbr_gpio_ctrl *gctrl = gpiochip_get_data(gc);
	unsigned int offset = irqd_to_hwirq(d);
	unsigned long flags;

	raw_spin_lock_irqsave(&gctrl->lock, flags);
	writel(BIT(offset), gctrl->membase + GPIO_IRNCR);
	raw_spin_unlock_irqrestore(&gctrl->lock, flags);
}

static void eqbr_gpio_mask_ack_irq(struct irq_data *d)
{
	eqbr_gpio_disable_irq(d);
	eqbr_gpio_ack_irq(d);
}

static inline void eqbr_cfg_bit(void __iomem *addr,
				unsigned int offset, unsigned int set)
{
	if (set)
		writel(readl(addr) | BIT(offset), addr);
	else
		writel(readl(addr) & ~BIT(offset), addr);
}

static int eqbr_irq_type_cfg(struct gpio_irq_type *type,
			     struct eqbr_gpio_ctrl *gctrl,
			     unsigned int offset)
{
	unsigned long flags;

	raw_spin_lock_irqsave(&gctrl->lock, flags);
	eqbr_cfg_bit(gctrl->membase + GPIO_IRNCFG, offset, type->trig_type);
	eqbr_cfg_bit(gctrl->membase + GPIO_EXINTCR1, offset, type->trig_type);
	eqbr_cfg_bit(gctrl->membase + GPIO_EXINTCR0, offset, type->logic_type);
	raw_spin_unlock_irqrestore(&gctrl->lock, flags);

	return 0;
}

static int eqbr_gpio_set_irq_type(struct irq_data *d, unsigned int type)
{
	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
	struct eqbr_gpio_ctrl *gctrl = gpiochip_get_data(gc);
	unsigned int offset = irqd_to_hwirq(d);
	struct gpio_irq_type it;

	memset(&it, 0, sizeof(it));

	if ((type & IRQ_TYPE_SENSE_MASK) == IRQ_TYPE_NONE)
		return 0;

	switch (type) {
	case IRQ_TYPE_EDGE_RISING:
		it.trig_type = GPIO_EDGE_TRIG;
		it.edge_type = GPIO_SINGLE_EDGE;
		it.logic_type = GPIO_POSITIVE_TRIG;
		break;

	case IRQ_TYPE_EDGE_FALLING:
		it.trig_type = GPIO_EDGE_TRIG;
		it.edge_type = GPIO_SINGLE_EDGE;
		it.logic_type = GPIO_NEGATIVE_TRIG;
		break;

	case IRQ_TYPE_EDGE_BOTH:
		it.trig_type = GPIO_EDGE_TRIG;
		it.edge_type = GPIO_BOTH_EDGE;
		it.logic_type = GPIO_POSITIVE_TRIG;
		break;

	case IRQ_TYPE_LEVEL_HIGH:
		it.trig_type = GPIO_LEVEL_TRIG;
		it.edge_type = GPIO_SINGLE_EDGE;
		it.logic_type = GPIO_POSITIVE_TRIG;
		break;

	case IRQ_TYPE_LEVEL_LOW:
		it.trig_type = GPIO_LEVEL_TRIG;
		it.edge_type = GPIO_SINGLE_EDGE;
		it.logic_type = GPIO_NEGATIVE_TRIG;
		break;

	default:
		return -EINVAL;
	}

	eqbr_irq_type_cfg(&it, gctrl, offset);
	if (it.trig_type == GPIO_EDGE_TRIG)
		irq_set_handler_locked(d, handle_edge_irq);
	else
		irq_set_handler_locked(d, handle_level_irq);

	return 0;
}

static void eqbr_irq_handler(struct irq_desc *desc)
{
	struct gpio_chip *gc = irq_desc_get_handler_data(desc);
	struct eqbr_gpio_ctrl *gctrl = gpiochip_get_data(gc);
	struct irq_chip *ic = irq_desc_get_chip(desc);
	unsigned long pins, offset;

	chained_irq_enter(ic, desc);
	pins = readl(gctrl->membase + GPIO_IRNCR);

	for_each_set_bit(offset, &pins, gc->ngpio)
		generic_handle_domain_irq(gc->irq.domain, offset);

	chained_irq_exit(ic, desc);
}

static const struct irq_chip eqbr_irq_chip = {
	.name = "gpio_irq",
	.irq_mask = eqbr_gpio_disable_irq,
	.irq_unmask = eqbr_gpio_enable_irq,
	.irq_ack = eqbr_gpio_ack_irq,
	.irq_mask_ack = eqbr_gpio_mask_ack_irq,
	.irq_set_type = eqbr_gpio_set_irq_type,
	.flags = IRQCHIP_IMMUTABLE,
	GPIOCHIP_IRQ_RESOURCE_HELPERS,
};

static int gpiochip_setup(struct device *dev, struct eqbr_gpio_ctrl *gctrl)
{
	struct gpio_irq_chip *girq;
	struct gpio_chip *gc;

	gc = &gctrl->chip;
	gc->label = gctrl->name;
	gc->fwnode = gctrl->fwnode;

	if (!fwnode_property_read_bool(gctrl->fwnode, "interrupt-controller")) {
		dev_dbg(dev, "gc %s: doesn't act as interrupt controller!\n",
			gctrl->name);
		return 0;
	}

	girq = &gctrl->chip.irq;
	gpio_irq_chip_set_chip(girq, &eqbr_irq_chip);
	girq->parent_handler = eqbr_irq_handler;
	girq->num_parents = 1;
	girq->parents = devm_kcalloc(dev, 1, sizeof(*girq->parents), GFP_KERNEL);
	if (!girq->parents)
		return -ENOMEM;

	girq->default_type = IRQ_TYPE_NONE;
	girq->handler = handle_bad_irq;
	girq->parents[0] = gctrl->virq;

	return 0;
}

static int gpiolib_reg(struct eqbr_pinctrl_drv_data *drvdata)
{
	struct device *dev = drvdata->dev;
	struct eqbr_gpio_ctrl *gctrl;
	struct device_node *np;
	struct resource res;
	int i, ret;

	for (i = 0; i < drvdata->nr_gpio_ctrls; i++) {
		gctrl = drvdata->gpio_ctrls + i;
		np = to_of_node(gctrl->fwnode);

		gctrl->name = devm_kasprintf(dev, GFP_KERNEL, "gpiochip%d", i);
		if (!gctrl->name)
			return -ENOMEM;

		if (of_address_to_resource(np, 0, &res)) {
			dev_err(dev, "Failed to get GPIO register address\n");
			return -ENXIO;
		}

		gctrl->membase = devm_ioremap_resource(dev, &res);
		if (IS_ERR(gctrl->membase))
			return PTR_ERR(gctrl->membase);

		gctrl->virq = irq_of_parse_and_map(np, 0);
		if (!gctrl->virq) {
			dev_err(dev, "%s: failed to parse and map irq\n",
				gctrl->name);
			return -ENXIO;
		}
		raw_spin_lock_init(&gctrl->lock);

		ret = bgpio_init(&gctrl->chip, dev, gctrl->bank->nr_pins / 8,
				 gctrl->membase + GPIO_IN,
				 gctrl->membase + GPIO_OUTSET,
				 gctrl->membase + GPIO_OUTCLR,
				 gctrl->membase + GPIO_DIR,
				 NULL, 0);
		if (ret) {
			dev_err(dev, "unable to init generic GPIO\n");
			return ret;
		}

		ret = gpiochip_setup(dev, gctrl);
		if (ret)
			return ret;

		ret = devm_gpiochip_add_data(dev, &gctrl->chip, gctrl);
		if (ret)
			return ret;
	}

	return 0;
}

static inline struct eqbr_pin_bank
*find_pinbank_via_pin(struct eqbr_pinctrl_drv_data *pctl, unsigned int pin)
{
	struct eqbr_pin_bank *bank;
	int i;

	for (i = 0; i < pctl->nr_banks; i++) {
		bank = &pctl->pin_banks[i];
		if (pin >= bank->pin_base &&
		    (pin - bank->pin_base) < bank->nr_pins)
			return bank;
	}

	return NULL;
}

static const struct pinctrl_ops eqbr_pctl_ops = {
	.get_groups_count	= pinctrl_generic_get_group_count,
	.get_group_name		= pinctrl_generic_get_group_name,
	.get_group_pins		= pinctrl_generic_get_group_pins,
	.dt_node_to_map		= pinconf_generic_dt_node_to_map_all,
	.dt_free_map		= pinconf_generic_dt_free_map,
};

static int eqbr_set_pin_mux(struct eqbr_pinctrl_drv_data *pctl,
			    unsigned int pmx, unsigned int pin)
{
	struct eqbr_pin_bank *bank;
	unsigned long flags;
	unsigned int offset;
	void __iomem *mem;

	bank = find_pinbank_via_pin(pctl, pin);
	if (!bank) {
		dev_err(pctl->dev, "Couldn't find pin bank for pin %u\n", pin);
		return -ENODEV;
	}
	mem = bank->membase;
	offset = pin - bank->pin_base;

	if (!(bank->aval_pinmap & BIT(offset))) {
		dev_err(pctl->dev,
			"PIN: %u is not valid, pinbase: %u, bitmap: %u\n",
			pin, bank->pin_base, bank->aval_pinmap);
		return -ENODEV;
	}

	raw_spin_lock_irqsave(&pctl->lock, flags);
	writel(pmx, mem + (offset * 4));
	raw_spin_unlock_irqrestore(&pctl->lock, flags);
	return 0;
}

static int eqbr_pinmux_set_mux(struct pinctrl_dev *pctldev,
			       unsigned int selector, unsigned int group)
{
	struct eqbr_pinctrl_drv_data *pctl = pinctrl_dev_get_drvdata(pctldev);
	struct function_desc *func;
	struct group_desc *grp;
	unsigned int *pinmux;
	int i;

	func = pinmux_generic_get_function(pctldev, selector);
	if (!func)
		return -EINVAL;

	grp = pinctrl_generic_get_group(pctldev, group);
	if (!grp)
		return -EINVAL;

	pinmux = grp->data;
	for (i = 0; i < grp->grp.npins; i++)
		eqbr_set_pin_mux(pctl, pinmux[i], grp->grp.pins[i]);

	return 0;
}

static int eqbr_pinmux_gpio_request(struct pinctrl_dev *pctldev,
				    struct pinctrl_gpio_range *range,
				    unsigned int pin)
{
	struct eqbr_pinctrl_drv_data *pctl = pinctrl_dev_get_drvdata(pctldev);

	return eqbr_set_pin_mux(pctl, EQBR_GPIO_MODE, pin);
}

static const struct pinmux_ops eqbr_pinmux_ops = {
	.get_functions_count	= pinmux_generic_get_function_count,
	.get_function_name	= pinmux_generic_get_function_name,
	.get_function_groups	= pinmux_generic_get_function_groups,
	.set_mux		= eqbr_pinmux_set_mux,
	.gpio_request_enable	= eqbr_pinmux_gpio_request,
	.strict			= true,
};

static int get_drv_cur(void __iomem *mem, unsigned int offset)
{
	unsigned int idx = offset / DRV_CUR_PINS; /* 0-15, 16-31 per register*/
	unsigned int pin_offset = offset % DRV_CUR_PINS;

	return PARSE_DRV_CURRENT(readl(mem + REG_DRCC(idx)), pin_offset);
}

static struct eqbr_gpio_ctrl
*get_gpio_ctrls_via_bank(struct eqbr_pinctrl_drv_data *pctl,
			struct eqbr_pin_bank *bank)
{
	int i;

	for (i = 0; i < pctl->nr_gpio_ctrls; i++) {
		if (pctl->gpio_ctrls[i].bank == bank)
			return &pctl->gpio_ctrls[i];
	}

	return NULL;
}

static int eqbr_pinconf_get(struct pinctrl_dev *pctldev, unsigned int pin,
			    unsigned long *config)
{
	struct eqbr_pinctrl_drv_data *pctl = pinctrl_dev_get_drvdata(pctldev);
	enum pin_config_param param = pinconf_to_config_param(*config);
	struct eqbr_gpio_ctrl *gctrl;
	struct eqbr_pin_bank *bank;
	unsigned long flags;
	unsigned int offset;
	void __iomem *mem;
	u32 val;

	bank = find_pinbank_via_pin(pctl, pin);
	if (!bank) {
		dev_err(pctl->dev, "Couldn't find pin bank for pin %u\n", pin);
		return -ENODEV;
	}
	mem = bank->membase;
	offset = pin - bank->pin_base;

	if (!(bank->aval_pinmap & BIT(offset))) {
		dev_err(pctl->dev,
			"PIN: %u is not valid, pinbase: %u, bitmap: %u\n",
			pin, bank->pin_base, bank->aval_pinmap);
		return -ENODEV;
	}

	raw_spin_lock_irqsave(&pctl->lock, flags);
	switch (param) {
	case PIN_CONFIG_BIAS_PULL_UP:
		val = !!(readl(mem + REG_PUEN) & BIT(offset));
		break;
	case PIN_CONFIG_BIAS_PULL_DOWN:
		val = !!(readl(mem + REG_PDEN) & BIT(offset));
		break;
	case PIN_CONFIG_DRIVE_OPEN_DRAIN:
		val = !!(readl(mem + REG_OD) & BIT(offset));
		break;
	case PIN_CONFIG_DRIVE_STRENGTH:
		val = get_drv_cur(mem, offset);
		break;
	case PIN_CONFIG_SLEW_RATE:
		val = !!(readl(mem + REG_SRC) & BIT(offset));
		break;
	case PIN_CONFIG_OUTPUT_ENABLE:
		gctrl = get_gpio_ctrls_via_bank(pctl, bank);
		if (!gctrl) {
			dev_err(pctl->dev, "Failed to find gpio via bank pinbase: %u, pin: %u\n",
				bank->pin_base, pin);
			raw_spin_unlock_irqrestore(&pctl->lock, flags);
			return -ENODEV;
		}
		val = !!(readl(gctrl->membase + GPIO_DIR) & BIT(offset));
		break;
	default:
		raw_spin_unlock_irqrestore(&pctl->lock, flags);
		return -ENOTSUPP;
	}
	raw_spin_unlock_irqrestore(&pctl->lock, flags);
	*config = pinconf_to_config_packed(param, val);
;
	return 0;
}

static int eqbr_pinconf_set(struct pinctrl_dev *pctldev, unsigned int pin,
			    unsigned long *configs, unsigned int num_configs)
{
	struct eqbr_pinctrl_drv_data *pctl = pinctrl_dev_get_drvdata(pctldev);
	struct eqbr_gpio_ctrl *gctrl;
	enum pin_config_param param;
	struct eqbr_pin_bank *bank;
	unsigned int val, offset;
	struct gpio_chip *gc;
	unsigned long flags;
	void __iomem *mem;
	u32 regval, mask;
	int i;

	for (i = 0; i < num_configs; i++) {
		param = pinconf_to_config_param(configs[i]);
		val = pinconf_to_config_argument(configs[i]);

		bank = find_pinbank_via_pin(pctl, pin);
		if (!bank) {
			dev_err(pctl->dev,
				"Couldn't find pin bank for pin %u\n", pin);
			return -ENODEV;
		}
		mem = bank->membase;
		offset = pin - bank->pin_base;

		switch (param) {
		case PIN_CONFIG_BIAS_PULL_UP:
			mem += REG_PUEN;
			mask = BIT(offset);
			break;
		case PIN_CONFIG_BIAS_PULL_DOWN:
			mem += REG_PDEN;
			mask = BIT(offset);
			break;
		case PIN_CONFIG_DRIVE_OPEN_DRAIN:
			mem += REG_OD;
			mask = BIT(offset);
			break;
		case PIN_CONFIG_DRIVE_STRENGTH:
			mem += REG_DRCC(offset / DRV_CUR_PINS);
			offset = (offset % DRV_CUR_PINS) * 2;
			mask = GENMASK(1, 0) << offset;
			break;
		case PIN_CONFIG_SLEW_RATE:
			mem += REG_SRC;
			mask = BIT(offset);
			break;
		case PIN_CONFIG_OUTPUT_ENABLE:
			gctrl = get_gpio_ctrls_via_bank(pctl, bank);
			if (!gctrl) {
				dev_err(pctl->dev, "Failed to find gpio via bank pinbase: %u, pin: %u\n",
					bank->pin_base, pin);
				return -ENODEV;
			}
			gc = &gctrl->chip;
			gc->direction_output(gc, offset, 0);
			continue;
		default:
			return -ENOTSUPP;
		}

		raw_spin_lock_irqsave(&pctl->lock, flags);
		regval = readl(mem);
		regval = (regval & ~mask) | ((val << offset) & mask);
		writel(regval, mem);
		raw_spin_unlock_irqrestore(&pctl->lock, flags);
	}

	return 0;
}

static int eqbr_pinconf_group_get(struct pinctrl_dev *pctldev,
				  unsigned int group, unsigned long *config)
{
	unsigned int i, npins, old = 0;
	const unsigned int *pins;
	int ret;

	ret = pinctrl_generic_get_group_pins(pctldev, group, &pins, &npins);
	if (ret)
		return ret;

	for (i = 0; i < npins; i++) {
		if (eqbr_pinconf_get(pctldev, pins[i], config))
			return -ENOTSUPP;

		if (i && old != *config)
			return -ENOTSUPP;

		old = *config;
	}
	return 0;
}

static int eqbr_pinconf_group_set(struct pinctrl_dev *pctldev,
				  unsigned int group, unsigned long *configs,
				  unsigned int num_configs)
{
	const unsigned int *pins;
	unsigned int i, npins;
	int ret;

	ret = pinctrl_generic_get_group_pins(pctldev, group, &pins, &npins);
	if (ret)
		return ret;

	for (i = 0; i < npins; i++) {
		ret = eqbr_pinconf_set(pctldev, pins[i], configs, num_configs);
		if (ret)
			return ret;
	}
	return 0;
}

static const struct pinconf_ops eqbr_pinconf_ops = {
	.is_generic			= true,
	.pin_config_get			= eqbr_pinconf_get,
	.pin_config_set			= eqbr_pinconf_set,
	.pin_config_group_get		= eqbr_pinconf_group_get,
	.pin_config_group_set		= eqbr_pinconf_group_set,
	.pin_config_config_dbg_show	= pinconf_generic_dump_config,
};

static bool is_func_exist(struct eqbr_pmx_func *funcs, const char *name,
			 unsigned int nr_funcs, unsigned int *idx)
{
	int i;

	if (!funcs)
		return false;

	for (i = 0; i < nr_funcs; i++) {
		if (funcs[i].name && !strcmp(funcs[i].name, name)) {
			*idx = i;
			return true;
		}
	}

	return false;
}

static int funcs_utils(struct device *dev, struct eqbr_pmx_func *funcs,
		       unsigned int *nr_funcs, funcs_util_ops op)
{
	struct device_node *node = dev->of_node;
	struct device_node *np;
	struct property *prop;
	const char *fn_name;
	unsigned int fid;
	int i, j;

	i = 0;
	for_each_child_of_node(node, np) {
		prop = of_find_property(np, "groups", NULL);
		if (!prop)
			continue;

		if (of_property_read_string(np, "function", &fn_name)) {
			/* some groups may not have function, it's OK */
			dev_dbg(dev, "Group %s: not function binded!\n",
				(char *)prop->value);
			continue;
		}

		switch (op) {
		case OP_COUNT_NR_FUNCS:
			if (!is_func_exist(funcs, fn_name, *nr_funcs, &fid))
				*nr_funcs = *nr_funcs + 1;
			break;

		case OP_ADD_FUNCS:
			if (!is_func_exist(funcs, fn_name, *nr_funcs, &fid))
				funcs[i].name = fn_name;
			break;

		case OP_COUNT_NR_FUNC_GRPS:
			if (is_func_exist(funcs, fn_name, *nr_funcs, &fid))
				funcs[fid].nr_groups++;
			break;

		case OP_ADD_FUNC_GRPS:
			if (is_func_exist(funcs, fn_name, *nr_funcs, &fid)) {
				for (j = 0; j < funcs[fid].nr_groups; j++)
					if (!funcs[fid].groups[j])
						break;
				funcs[fid].groups[j] = prop->value;
			}
			break;

		default:
			of_node_put(np);
			return -EINVAL;
		}
		i++;
	}

	return 0;
}

static int eqbr_build_functions(struct eqbr_pinctrl_drv_data *drvdata)
{
	struct device *dev = drvdata->dev;
	struct eqbr_pmx_func *funcs = NULL;
	unsigned int nr_funcs = 0;
	int i, ret;

	ret = funcs_utils(dev, funcs, &nr_funcs, OP_COUNT_NR_FUNCS);
	if (ret)
		return ret;

	funcs = devm_kcalloc(dev, nr_funcs, sizeof(*funcs), GFP_KERNEL);
	if (!funcs)
		return -ENOMEM;

	ret = funcs_utils(dev, funcs, &nr_funcs, OP_ADD_FUNCS);
	if (ret)
		return ret;

	ret = funcs_utils(dev, funcs, &nr_funcs, OP_COUNT_NR_FUNC_GRPS);
	if (ret)
		return ret;

	for (i = 0; i < nr_funcs; i++) {
		if (!funcs[i].nr_groups)
			continue;
		funcs[i].groups = devm_kcalloc(dev, funcs[i].nr_groups,
					       sizeof(*(funcs[i].groups)),
					       GFP_KERNEL);
		if (!funcs[i].groups)
			return -ENOMEM;
	}

	ret = funcs_utils(dev, funcs, &nr_funcs, OP_ADD_FUNC_GRPS);
	if (ret)
		return ret;

	for (i = 0; i < nr_funcs; i++) {

		/* Ignore the same function with multiple groups */
		if (funcs[i].name == NULL)
			continue;

		ret = pinmux_generic_add_function(drvdata->pctl_dev,
						  funcs[i].name,
						  funcs[i].groups,
						  funcs[i].nr_groups,
						  drvdata);
		if (ret < 0) {
			dev_err(dev, "Failed to register function %s\n",
				funcs[i].name);
			return ret;
		}
	}

	return 0;
}

static int eqbr_build_groups(struct eqbr_pinctrl_drv_data *drvdata)
{
	struct device *dev = drvdata->dev;
	struct device_node *node = dev->of_node;
	unsigned int *pins, *pinmux, pin_id, pinmux_id;
	struct pingroup group, *grp = &group;
	struct device_node *np;
	struct property *prop;
	int j, err;

	for_each_child_of_node(node, np) {
		prop = of_find_property(np, "groups", NULL);
		if (!prop)
			continue;

		err = of_property_count_u32_elems(np, "pins");
		if (err < 0) {
			dev_err(dev, "No pins in the group: %s\n", prop->name);
			of_node_put(np);
			return err;
		}
		grp->npins = err;
		grp->name = prop->value;
		pins = devm_kcalloc(dev, grp->npins, sizeof(*pins), GFP_KERNEL);
		if (!pins) {
			of_node_put(np);
			return -ENOMEM;
		}
		grp->pins = pins;

		pinmux = devm_kcalloc(dev, grp->npins, sizeof(*pinmux), GFP_KERNEL);
		if (!pinmux) {
			of_node_put(np);
			return -ENOMEM;
		}

		for (j = 0; j < grp->npins; j++) {
			if (of_property_read_u32_index(np, "pins", j, &pin_id)) {
				dev_err(dev, "Group %s: Read intel pins id failed\n",
					grp->name);
				of_node_put(np);
				return -EINVAL;
			}
			if (pin_id >= drvdata->pctl_desc.npins) {
				dev_err(dev, "Group %s: Invalid pin ID, idx: %d, pin %u\n",
					grp->name, j, pin_id);
				of_node_put(np);
				return -EINVAL;
			}
			pins[j] = pin_id;
			if (of_property_read_u32_index(np, "pinmux", j, &pinmux_id)) {
				dev_err(dev, "Group %s: Read intel pinmux id failed\n",
					grp->name);
				of_node_put(np);
				return -EINVAL;
			}
			pinmux[j] = pinmux_id;
		}

		err = pinctrl_generic_add_group(drvdata->pctl_dev,
						grp->name, grp->pins, grp->npins,
						pinmux);
		if (err < 0) {
			dev_err(dev, "Failed to register group %s\n", grp->name);
			of_node_put(np);
			return err;
		}
		memset(&group, 0, sizeof(group));
		pinmux = NULL;
	}

	return 0;
}

static int pinctrl_reg(struct eqbr_pinctrl_drv_data *drvdata)
{
	struct pinctrl_desc *pctl_desc;
	struct pinctrl_pin_desc *pdesc;
	struct device *dev;
	unsigned int nr_pins;
	char *pin_names;
	int i, ret;

	dev = drvdata->dev;
	pctl_desc = &drvdata->pctl_desc;
	pctl_desc->name = "eqbr-pinctrl";
	pctl_desc->owner = THIS_MODULE;
	pctl_desc->pctlops = &eqbr_pctl_ops;
	pctl_desc->pmxops = &eqbr_pinmux_ops;
	pctl_desc->confops = &eqbr_pinconf_ops;
	raw_spin_lock_init(&drvdata->lock);

	for (i = 0, nr_pins = 0; i < drvdata->nr_banks; i++)
		nr_pins += drvdata->pin_banks[i].nr_pins;

	pdesc = devm_kcalloc(dev, nr_pins, sizeof(*pdesc), GFP_KERNEL);
	if (!pdesc)
		return -ENOMEM;
	pin_names = devm_kcalloc(dev, nr_pins, PIN_NAME_LEN, GFP_KERNEL);
	if (!pin_names)
		return -ENOMEM;

	for (i = 0; i < nr_pins; i++) {
		sprintf(pin_names, PIN_NAME_FMT, i);
		pdesc[i].number = i;
		pdesc[i].name = pin_names;
		pin_names += PIN_NAME_LEN;
	}
	pctl_desc->pins = pdesc;
	pctl_desc->npins = nr_pins;
	dev_dbg(dev, "pinctrl total pin number: %u\n", nr_pins);

	ret = devm_pinctrl_register_and_init(dev, pctl_desc, drvdata,
					     &drvdata->pctl_dev);
	if (ret)
		return ret;

	ret = eqbr_build_groups(drvdata);
	if (ret) {
		dev_err(dev, "Failed to build groups\n");
		return ret;
	}

	ret = eqbr_build_functions(drvdata);
	if (ret) {
		dev_err(dev, "Failed to build functions\n");
		return ret;
	}

	return pinctrl_enable(drvdata->pctl_dev);
}

static int pinbank_init(struct device_node *np,
			struct eqbr_pinctrl_drv_data *drvdata,
			struct eqbr_pin_bank *bank, unsigned int id)
{
	struct device *dev = drvdata->dev;
	struct of_phandle_args spec;
	int ret;

	bank->membase = drvdata->membase + id * PAD_REG_OFF;

	ret = of_parse_phandle_with_fixed_args(np, "gpio-ranges", 3, 0, &spec);
	if (ret) {
		dev_err(dev, "gpio-range not available!\n");
		return ret;
	}

	bank->pin_base = spec.args[1];
	bank->nr_pins = spec.args[2];

	bank->aval_pinmap = readl(bank->membase + REG_AVAIL);
	bank->id = id;

	dev_dbg(dev, "pinbank id: %d, reg: %px, pinbase: %u, pin number: %u, pinmap: 0x%x\n",
		id, bank->membase, bank->pin_base,
		bank->nr_pins, bank->aval_pinmap);

	return ret;
}

static int pinbank_probe(struct eqbr_pinctrl_drv_data *drvdata)
{
	struct device *dev = drvdata->dev;
	struct device_node *np_gpio;
	struct eqbr_gpio_ctrl *gctrls;
	struct eqbr_pin_bank *banks;
	int i, nr_gpio;

	/* Count gpio bank number */
	nr_gpio = 0;
	for_each_node_by_name(np_gpio, "gpio") {
		if (of_device_is_available(np_gpio))
			nr_gpio++;
	}

	if (!nr_gpio) {
		dev_err(dev, "NO pin bank available!\n");
		return -ENODEV;
	}

	/* Count pin bank number and gpio controller number */
	banks = devm_kcalloc(dev, nr_gpio, sizeof(*banks), GFP_KERNEL);
	if (!banks)
		return -ENOMEM;

	gctrls = devm_kcalloc(dev, nr_gpio, sizeof(*gctrls), GFP_KERNEL);
	if (!gctrls)
		return -ENOMEM;

	dev_dbg(dev, "found %d gpio controller!\n", nr_gpio);

	/* Initialize Pin bank */
	i = 0;
	for_each_node_by_name(np_gpio, "gpio") {
		if (!of_device_is_available(np_gpio))
			continue;

		pinbank_init(np_gpio, drvdata, banks + i, i);

		gctrls[i].fwnode = of_fwnode_handle(np_gpio);
		gctrls[i].bank = banks + i;
		i++;
	}

	drvdata->pin_banks = banks;
	drvdata->nr_banks = nr_gpio;
	drvdata->gpio_ctrls = gctrls;
	drvdata->nr_gpio_ctrls = nr_gpio;

	return 0;
}

static int eqbr_pinctrl_probe(struct platform_device *pdev)
{
	struct eqbr_pinctrl_drv_data *drvdata;
	struct device *dev = &pdev->dev;
	int ret;

	drvdata = devm_kzalloc(dev, sizeof(*drvdata), GFP_KERNEL);
	if (!drvdata)
		return -ENOMEM;

	drvdata->dev = dev;

	drvdata->membase = devm_platform_ioremap_resource(pdev, 0);
	if (IS_ERR(drvdata->membase))
		return PTR_ERR(drvdata->membase);

	ret = pinbank_probe(drvdata);
	if (ret)
		return ret;

	ret = pinctrl_reg(drvdata);
	if (ret)
		return ret;

	ret = gpiolib_reg(drvdata);
	if (ret)
		return ret;

	platform_set_drvdata(pdev, drvdata);
	return 0;
}

static const struct of_device_id eqbr_pinctrl_dt_match[] = {
	{ .compatible = "intel,lgm-io" },
	{}
};
MODULE_DEVICE_TABLE(of, eqbr_pinctrl_dt_match);

static struct platform_driver eqbr_pinctrl_driver = {
	.probe	= eqbr_pinctrl_probe,
	.driver = {
		.name = "eqbr-pinctrl",
		.of_match_table = eqbr_pinctrl_dt_match,
	},
};

module_platform_driver(eqbr_pinctrl_driver);

MODULE_AUTHOR("Zhu Yixin <yixin.zhu@intel.com>, Rahul Tanwar <rahul.tanwar@intel.com>");
MODULE_DESCRIPTION("Pinctrl Driver for LGM SoC (Equilibrium)");
MODULE_LICENSE("GPL v2");
