cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

pinctrl-plgpio.c (18913B)


      1/*
      2 * SPEAr platform PLGPIO driver
      3 *
      4 * Copyright (C) 2012 ST Microelectronics
      5 * Viresh Kumar <viresh.kumar@linaro.org>
      6 *
      7 * This file is licensed under the terms of the GNU General Public
      8 * License version 2. This program is licensed "as is" without any
      9 * warranty of any kind, whether express or implied.
     10 */
     11
     12#include <linux/clk.h>
     13#include <linux/err.h>
     14#include <linux/gpio/driver.h>
     15#include <linux/io.h>
     16#include <linux/init.h>
     17#include <linux/mfd/syscon.h>
     18#include <linux/of.h>
     19#include <linux/of_platform.h>
     20#include <linux/pinctrl/consumer.h>
     21#include <linux/platform_device.h>
     22#include <linux/pm.h>
     23#include <linux/regmap.h>
     24#include <linux/spinlock.h>
     25
     26#define MAX_GPIO_PER_REG		32
     27#define PIN_OFFSET(pin)			(pin % MAX_GPIO_PER_REG)
     28#define REG_OFFSET(base, reg, pin)	(base + reg + (pin / MAX_GPIO_PER_REG) \
     29							* sizeof(int *))
     30
     31/*
     32 * plgpio pins in all machines are not one to one mapped, bitwise with registers
     33 * bits. These set of macros define register masks for which below functions
     34 * (pin_to_offset and offset_to_pin) are required to be called.
     35 */
     36#define PTO_ENB_REG		0x001
     37#define PTO_WDATA_REG		0x002
     38#define PTO_DIR_REG		0x004
     39#define PTO_IE_REG		0x008
     40#define PTO_RDATA_REG		0x010
     41#define PTO_MIS_REG		0x020
     42
     43struct plgpio_regs {
     44	u32 enb;		/* enable register */
     45	u32 wdata;		/* write data register */
     46	u32 dir;		/* direction set register */
     47	u32 rdata;		/* read data register */
     48	u32 ie;			/* interrupt enable register */
     49	u32 mis;		/* mask interrupt status register */
     50	u32 eit;		/* edge interrupt type */
     51};
     52
     53/*
     54 * struct plgpio: plgpio driver specific structure
     55 *
     56 * lock: lock for guarding gpio registers
     57 * base: base address of plgpio block
     58 * chip: gpio framework specific chip information structure
     59 * p2o: function ptr for pin to offset conversion. This is required only for
     60 *	machines where mapping b/w pin and offset is not 1-to-1.
     61 * o2p: function ptr for offset to pin conversion. This is required only for
     62 *	machines where mapping b/w pin and offset is not 1-to-1.
     63 * p2o_regs: mask of registers for which p2o and o2p are applicable
     64 * regs: register offsets
     65 * csave_regs: context save registers for standby/sleep/hibernate cases
     66 */
     67struct plgpio {
     68	spinlock_t		lock;
     69	struct regmap		*regmap;
     70	struct clk		*clk;
     71	struct gpio_chip	chip;
     72	int			(*p2o)(int pin);	/* pin_to_offset */
     73	int			(*o2p)(int offset);	/* offset_to_pin */
     74	u32			p2o_regs;
     75	struct plgpio_regs	regs;
     76#ifdef CONFIG_PM_SLEEP
     77	struct plgpio_regs	*csave_regs;
     78#endif
     79};
     80
     81/* register manipulation inline functions */
     82static inline u32 is_plgpio_set(struct regmap *regmap, u32 pin, u32 reg)
     83{
     84	u32 offset = PIN_OFFSET(pin);
     85	u32 reg_off = REG_OFFSET(0, reg, pin);
     86	u32 val;
     87
     88	regmap_read(regmap, reg_off, &val);
     89
     90	return !!(val & (1 << offset));
     91}
     92
     93static inline void plgpio_reg_set(struct regmap *regmap, u32 pin, u32 reg)
     94{
     95	u32 offset = PIN_OFFSET(pin);
     96	u32 reg_off = REG_OFFSET(0, reg, pin);
     97	u32 mask;
     98
     99	mask = 1 << offset;
    100	regmap_update_bits(regmap, reg_off, mask, mask);
    101}
    102
    103static inline void plgpio_reg_reset(struct regmap *regmap, u32 pin, u32 reg)
    104{
    105	u32 offset = PIN_OFFSET(pin);
    106	u32 reg_off = REG_OFFSET(0, reg, pin);
    107	u32 mask;
    108
    109	mask = 1 << offset;
    110	regmap_update_bits(regmap, reg_off, mask, 0);
    111}
    112
    113
    114/* gpio framework specific routines */
    115static int plgpio_direction_input(struct gpio_chip *chip, unsigned offset)
    116{
    117	struct plgpio *plgpio = gpiochip_get_data(chip);
    118	unsigned long flags;
    119
    120	/* get correct offset for "offset" pin */
    121	if (plgpio->p2o && (plgpio->p2o_regs & PTO_DIR_REG)) {
    122		offset = plgpio->p2o(offset);
    123		if (offset == -1)
    124			return -EINVAL;
    125	}
    126
    127	spin_lock_irqsave(&plgpio->lock, flags);
    128	plgpio_reg_set(plgpio->regmap, offset, plgpio->regs.dir);
    129	spin_unlock_irqrestore(&plgpio->lock, flags);
    130
    131	return 0;
    132}
    133
    134static int plgpio_direction_output(struct gpio_chip *chip, unsigned offset,
    135		int value)
    136{
    137	struct plgpio *plgpio = gpiochip_get_data(chip);
    138	unsigned long flags;
    139	unsigned dir_offset = offset, wdata_offset = offset, tmp;
    140
    141	/* get correct offset for "offset" pin */
    142	if (plgpio->p2o && (plgpio->p2o_regs & (PTO_DIR_REG | PTO_WDATA_REG))) {
    143		tmp = plgpio->p2o(offset);
    144		if (tmp == -1)
    145			return -EINVAL;
    146
    147		if (plgpio->p2o_regs & PTO_DIR_REG)
    148			dir_offset = tmp;
    149		if (plgpio->p2o_regs & PTO_WDATA_REG)
    150			wdata_offset = tmp;
    151	}
    152
    153	spin_lock_irqsave(&plgpio->lock, flags);
    154	if (value)
    155		plgpio_reg_set(plgpio->regmap, wdata_offset,
    156				plgpio->regs.wdata);
    157	else
    158		plgpio_reg_reset(plgpio->regmap, wdata_offset,
    159				plgpio->regs.wdata);
    160
    161	plgpio_reg_reset(plgpio->regmap, dir_offset, plgpio->regs.dir);
    162	spin_unlock_irqrestore(&plgpio->lock, flags);
    163
    164	return 0;
    165}
    166
    167static int plgpio_get_value(struct gpio_chip *chip, unsigned offset)
    168{
    169	struct plgpio *plgpio = gpiochip_get_data(chip);
    170
    171	if (offset >= chip->ngpio)
    172		return -EINVAL;
    173
    174	/* get correct offset for "offset" pin */
    175	if (plgpio->p2o && (plgpio->p2o_regs & PTO_RDATA_REG)) {
    176		offset = plgpio->p2o(offset);
    177		if (offset == -1)
    178			return -EINVAL;
    179	}
    180
    181	return is_plgpio_set(plgpio->regmap, offset, plgpio->regs.rdata);
    182}
    183
    184static void plgpio_set_value(struct gpio_chip *chip, unsigned offset, int value)
    185{
    186	struct plgpio *plgpio = gpiochip_get_data(chip);
    187
    188	if (offset >= chip->ngpio)
    189		return;
    190
    191	/* get correct offset for "offset" pin */
    192	if (plgpio->p2o && (plgpio->p2o_regs & PTO_WDATA_REG)) {
    193		offset = plgpio->p2o(offset);
    194		if (offset == -1)
    195			return;
    196	}
    197
    198	if (value)
    199		plgpio_reg_set(plgpio->regmap, offset, plgpio->regs.wdata);
    200	else
    201		plgpio_reg_reset(plgpio->regmap, offset, plgpio->regs.wdata);
    202}
    203
    204static int plgpio_request(struct gpio_chip *chip, unsigned offset)
    205{
    206	struct plgpio *plgpio = gpiochip_get_data(chip);
    207	int gpio = chip->base + offset;
    208	unsigned long flags;
    209	int ret = 0;
    210
    211	if (offset >= chip->ngpio)
    212		return -EINVAL;
    213
    214	ret = pinctrl_gpio_request(gpio);
    215	if (ret)
    216		return ret;
    217
    218	if (!IS_ERR(plgpio->clk)) {
    219		ret = clk_enable(plgpio->clk);
    220		if (ret)
    221			goto err0;
    222	}
    223
    224	if (plgpio->regs.enb == -1)
    225		return 0;
    226
    227	/*
    228	 * put gpio in IN mode before enabling it. This make enabling gpio safe
    229	 */
    230	ret = plgpio_direction_input(chip, offset);
    231	if (ret)
    232		goto err1;
    233
    234	/* get correct offset for "offset" pin */
    235	if (plgpio->p2o && (plgpio->p2o_regs & PTO_ENB_REG)) {
    236		offset = plgpio->p2o(offset);
    237		if (offset == -1) {
    238			ret = -EINVAL;
    239			goto err1;
    240		}
    241	}
    242
    243	spin_lock_irqsave(&plgpio->lock, flags);
    244	plgpio_reg_set(plgpio->regmap, offset, plgpio->regs.enb);
    245	spin_unlock_irqrestore(&plgpio->lock, flags);
    246	return 0;
    247
    248err1:
    249	if (!IS_ERR(plgpio->clk))
    250		clk_disable(plgpio->clk);
    251err0:
    252	pinctrl_gpio_free(gpio);
    253	return ret;
    254}
    255
    256static void plgpio_free(struct gpio_chip *chip, unsigned offset)
    257{
    258	struct plgpio *plgpio = gpiochip_get_data(chip);
    259	int gpio = chip->base + offset;
    260	unsigned long flags;
    261
    262	if (offset >= chip->ngpio)
    263		return;
    264
    265	if (plgpio->regs.enb == -1)
    266		goto disable_clk;
    267
    268	/* get correct offset for "offset" pin */
    269	if (plgpio->p2o && (plgpio->p2o_regs & PTO_ENB_REG)) {
    270		offset = plgpio->p2o(offset);
    271		if (offset == -1)
    272			return;
    273	}
    274
    275	spin_lock_irqsave(&plgpio->lock, flags);
    276	plgpio_reg_reset(plgpio->regmap, offset, plgpio->regs.enb);
    277	spin_unlock_irqrestore(&plgpio->lock, flags);
    278
    279disable_clk:
    280	if (!IS_ERR(plgpio->clk))
    281		clk_disable(plgpio->clk);
    282
    283	pinctrl_gpio_free(gpio);
    284}
    285
    286/* PLGPIO IRQ */
    287static void plgpio_irq_disable(struct irq_data *d)
    288{
    289	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
    290	struct plgpio *plgpio = gpiochip_get_data(gc);
    291	int offset = d->hwirq;
    292	unsigned long flags;
    293
    294	/* get correct offset for "offset" pin */
    295	if (plgpio->p2o && (plgpio->p2o_regs & PTO_IE_REG)) {
    296		offset = plgpio->p2o(offset);
    297		if (offset == -1)
    298			return;
    299	}
    300
    301	spin_lock_irqsave(&plgpio->lock, flags);
    302	plgpio_reg_set(plgpio->regmap, offset, plgpio->regs.ie);
    303	spin_unlock_irqrestore(&plgpio->lock, flags);
    304}
    305
    306static void plgpio_irq_enable(struct irq_data *d)
    307{
    308	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
    309	struct plgpio *plgpio = gpiochip_get_data(gc);
    310	int offset = d->hwirq;
    311	unsigned long flags;
    312
    313	/* get correct offset for "offset" pin */
    314	if (plgpio->p2o && (plgpio->p2o_regs & PTO_IE_REG)) {
    315		offset = plgpio->p2o(offset);
    316		if (offset == -1)
    317			return;
    318	}
    319
    320	spin_lock_irqsave(&plgpio->lock, flags);
    321	plgpio_reg_reset(plgpio->regmap, offset, plgpio->regs.ie);
    322	spin_unlock_irqrestore(&plgpio->lock, flags);
    323}
    324
    325static int plgpio_irq_set_type(struct irq_data *d, unsigned trigger)
    326{
    327	struct gpio_chip *gc = irq_data_get_irq_chip_data(d);
    328	struct plgpio *plgpio = gpiochip_get_data(gc);
    329	int offset = d->hwirq;
    330	u32 reg_off;
    331	unsigned int supported_type = 0, val;
    332
    333	if (offset >= plgpio->chip.ngpio)
    334		return -EINVAL;
    335
    336	if (plgpio->regs.eit == -1)
    337		supported_type = IRQ_TYPE_LEVEL_HIGH;
    338	else
    339		supported_type = IRQ_TYPE_EDGE_RISING | IRQ_TYPE_EDGE_FALLING;
    340
    341	if (!(trigger & supported_type))
    342		return -EINVAL;
    343
    344	if (plgpio->regs.eit == -1)
    345		return 0;
    346
    347	reg_off = REG_OFFSET(0, plgpio->regs.eit, offset);
    348	regmap_read(plgpio->regmap, reg_off, &val);
    349
    350	offset = PIN_OFFSET(offset);
    351	if (trigger & IRQ_TYPE_EDGE_RISING)
    352		regmap_write(plgpio->regmap, reg_off, val | (1 << offset));
    353	else
    354		regmap_write(plgpio->regmap, reg_off, val & ~(1 << offset));
    355
    356	return 0;
    357}
    358
    359static struct irq_chip plgpio_irqchip = {
    360	.name		= "PLGPIO",
    361	.irq_enable	= plgpio_irq_enable,
    362	.irq_disable	= plgpio_irq_disable,
    363	.irq_set_type	= plgpio_irq_set_type,
    364};
    365
    366static void plgpio_irq_handler(struct irq_desc *desc)
    367{
    368	struct gpio_chip *gc = irq_desc_get_handler_data(desc);
    369	struct plgpio *plgpio = gpiochip_get_data(gc);
    370	struct irq_chip *irqchip = irq_desc_get_chip(desc);
    371	int regs_count, count, pin, offset, i = 0;
    372	u32 pending;
    373	unsigned long pendingl;
    374
    375	count = plgpio->chip.ngpio;
    376	regs_count = DIV_ROUND_UP(count, MAX_GPIO_PER_REG);
    377
    378	chained_irq_enter(irqchip, desc);
    379	/* check all plgpio MIS registers for a possible interrupt */
    380	for (; i < regs_count; i++) {
    381		regmap_read(plgpio->regmap, plgpio->regs.mis +
    382			i * sizeof(int *), &pending);
    383		if (!pending)
    384			continue;
    385
    386		/* clear interrupts */
    387		regmap_write(plgpio->regmap, plgpio->regs.mis +
    388			i * sizeof(int *), ~pending);
    389		/*
    390		 * clear extra bits in last register having gpios < MAX/REG
    391		 * ex: Suppose there are max 102 plgpios. then last register
    392		 * must have only (102 - MAX_GPIO_PER_REG * 3) = 6 relevant bits
    393		 * so, we must not take other 28 bits into consideration for
    394		 * checking interrupt. so clear those bits.
    395		 */
    396		count = count - i * MAX_GPIO_PER_REG;
    397		if (count < MAX_GPIO_PER_REG)
    398			pending &= (1 << count) - 1;
    399
    400		pendingl = pending;
    401		for_each_set_bit(offset, &pendingl, MAX_GPIO_PER_REG) {
    402			/* get correct pin for "offset" */
    403			if (plgpio->o2p && (plgpio->p2o_regs & PTO_MIS_REG)) {
    404				pin = plgpio->o2p(offset);
    405				if (pin == -1)
    406					continue;
    407			} else
    408				pin = offset;
    409
    410			/* get correct irq line number */
    411			pin = i * MAX_GPIO_PER_REG + pin;
    412			generic_handle_domain_irq(gc->irq.domain, pin);
    413		}
    414	}
    415	chained_irq_exit(irqchip, desc);
    416}
    417
    418/*
    419 * pin to offset and offset to pin converter functions
    420 *
    421 * In spear310 there is inconsistency among bit positions in plgpio regiseters,
    422 * for different plgpio pins. For example: for pin 27, bit offset is 23, pin
    423 * 28-33 are not supported, pin 95 has offset bit 95, bit 100 has offset bit 1
    424 */
    425static int spear310_p2o(int pin)
    426{
    427	int offset = pin;
    428
    429	if (pin <= 27)
    430		offset += 4;
    431	else if (pin <= 33)
    432		offset = -1;
    433	else if (pin <= 97)
    434		offset -= 2;
    435	else if (pin <= 101)
    436		offset = 101 - pin;
    437	else
    438		offset = -1;
    439
    440	return offset;
    441}
    442
    443static int spear310_o2p(int offset)
    444{
    445	if (offset <= 3)
    446		return 101 - offset;
    447	else if (offset <= 31)
    448		return offset - 4;
    449	else
    450		return offset + 2;
    451}
    452
    453static int plgpio_probe_dt(struct platform_device *pdev, struct plgpio *plgpio)
    454{
    455	struct device_node *np = pdev->dev.of_node;
    456	int ret = -EINVAL;
    457	u32 val;
    458
    459	if (of_machine_is_compatible("st,spear310")) {
    460		plgpio->p2o = spear310_p2o;
    461		plgpio->o2p = spear310_o2p;
    462		plgpio->p2o_regs = PTO_WDATA_REG | PTO_DIR_REG | PTO_IE_REG |
    463			PTO_RDATA_REG | PTO_MIS_REG;
    464	}
    465
    466	if (!of_property_read_u32(np, "st-plgpio,ngpio", &val)) {
    467		plgpio->chip.ngpio = val;
    468	} else {
    469		dev_err(&pdev->dev, "DT: Invalid ngpio field\n");
    470		goto end;
    471	}
    472
    473	if (!of_property_read_u32(np, "st-plgpio,enb-reg", &val))
    474		plgpio->regs.enb = val;
    475	else
    476		plgpio->regs.enb = -1;
    477
    478	if (!of_property_read_u32(np, "st-plgpio,wdata-reg", &val)) {
    479		plgpio->regs.wdata = val;
    480	} else {
    481		dev_err(&pdev->dev, "DT: Invalid wdata reg\n");
    482		goto end;
    483	}
    484
    485	if (!of_property_read_u32(np, "st-plgpio,dir-reg", &val)) {
    486		plgpio->regs.dir = val;
    487	} else {
    488		dev_err(&pdev->dev, "DT: Invalid dir reg\n");
    489		goto end;
    490	}
    491
    492	if (!of_property_read_u32(np, "st-plgpio,ie-reg", &val)) {
    493		plgpio->regs.ie = val;
    494	} else {
    495		dev_err(&pdev->dev, "DT: Invalid ie reg\n");
    496		goto end;
    497	}
    498
    499	if (!of_property_read_u32(np, "st-plgpio,rdata-reg", &val)) {
    500		plgpio->regs.rdata = val;
    501	} else {
    502		dev_err(&pdev->dev, "DT: Invalid rdata reg\n");
    503		goto end;
    504	}
    505
    506	if (!of_property_read_u32(np, "st-plgpio,mis-reg", &val)) {
    507		plgpio->regs.mis = val;
    508	} else {
    509		dev_err(&pdev->dev, "DT: Invalid mis reg\n");
    510		goto end;
    511	}
    512
    513	if (!of_property_read_u32(np, "st-plgpio,eit-reg", &val))
    514		plgpio->regs.eit = val;
    515	else
    516		plgpio->regs.eit = -1;
    517
    518	return 0;
    519
    520end:
    521	return ret;
    522}
    523
    524static int plgpio_probe(struct platform_device *pdev)
    525{
    526	struct device_node *regmap_np;
    527	struct plgpio *plgpio;
    528	int ret, irq;
    529
    530	plgpio = devm_kzalloc(&pdev->dev, sizeof(*plgpio), GFP_KERNEL);
    531	if (!plgpio)
    532		return -ENOMEM;
    533
    534	regmap_np = of_parse_phandle(pdev->dev.of_node, "regmap", 0);
    535	if (regmap_np) {
    536		plgpio->regmap = device_node_to_regmap(regmap_np);
    537		of_node_put(regmap_np);
    538		if (IS_ERR(plgpio->regmap)) {
    539			dev_err(&pdev->dev, "Retrieve regmap failed (%pe)\n",
    540				plgpio->regmap);
    541			return PTR_ERR(plgpio->regmap);
    542		}
    543	} else {
    544		plgpio->regmap = device_node_to_regmap(pdev->dev.of_node);
    545		if (IS_ERR(plgpio->regmap)) {
    546			dev_err(&pdev->dev, "Init regmap failed (%pe)\n",
    547				plgpio->regmap);
    548			return PTR_ERR(plgpio->regmap);
    549		}
    550	}
    551
    552	ret = plgpio_probe_dt(pdev, plgpio);
    553	if (ret) {
    554		dev_err(&pdev->dev, "DT probe failed\n");
    555		return ret;
    556	}
    557
    558	plgpio->clk = devm_clk_get(&pdev->dev, NULL);
    559	if (IS_ERR(plgpio->clk))
    560		dev_warn(&pdev->dev, "clk_get() failed, work without it\n");
    561
    562#ifdef CONFIG_PM_SLEEP
    563	plgpio->csave_regs = devm_kcalloc(&pdev->dev,
    564			DIV_ROUND_UP(plgpio->chip.ngpio, MAX_GPIO_PER_REG),
    565			sizeof(*plgpio->csave_regs),
    566			GFP_KERNEL);
    567	if (!plgpio->csave_regs)
    568		return -ENOMEM;
    569#endif
    570
    571	platform_set_drvdata(pdev, plgpio);
    572	spin_lock_init(&plgpio->lock);
    573
    574	plgpio->chip.base = -1;
    575	plgpio->chip.request = plgpio_request;
    576	plgpio->chip.free = plgpio_free;
    577	plgpio->chip.direction_input = plgpio_direction_input;
    578	plgpio->chip.direction_output = plgpio_direction_output;
    579	plgpio->chip.get = plgpio_get_value;
    580	plgpio->chip.set = plgpio_set_value;
    581	plgpio->chip.label = dev_name(&pdev->dev);
    582	plgpio->chip.parent = &pdev->dev;
    583	plgpio->chip.owner = THIS_MODULE;
    584
    585	if (!IS_ERR(plgpio->clk)) {
    586		ret = clk_prepare(plgpio->clk);
    587		if (ret) {
    588			dev_err(&pdev->dev, "clk prepare failed\n");
    589			return ret;
    590		}
    591	}
    592
    593	irq = platform_get_irq(pdev, 0);
    594	if (irq > 0) {
    595		struct gpio_irq_chip *girq;
    596
    597		girq = &plgpio->chip.irq;
    598		girq->chip = &plgpio_irqchip;
    599		girq->parent_handler = plgpio_irq_handler;
    600		girq->num_parents = 1;
    601		girq->parents = devm_kcalloc(&pdev->dev, 1,
    602					     sizeof(*girq->parents),
    603					     GFP_KERNEL);
    604		if (!girq->parents)
    605			return -ENOMEM;
    606		girq->parents[0] = irq;
    607		girq->default_type = IRQ_TYPE_NONE;
    608		girq->handler = handle_simple_irq;
    609		dev_info(&pdev->dev, "PLGPIO registering with IRQs\n");
    610	} else {
    611		dev_info(&pdev->dev, "PLGPIO registering without IRQs\n");
    612	}
    613
    614	ret = gpiochip_add_data(&plgpio->chip, plgpio);
    615	if (ret) {
    616		dev_err(&pdev->dev, "unable to add gpio chip\n");
    617		goto unprepare_clk;
    618	}
    619
    620	return 0;
    621
    622unprepare_clk:
    623	if (!IS_ERR(plgpio->clk))
    624		clk_unprepare(plgpio->clk);
    625
    626	return ret;
    627}
    628
    629#ifdef CONFIG_PM_SLEEP
    630static int plgpio_suspend(struct device *dev)
    631{
    632	struct plgpio *plgpio = dev_get_drvdata(dev);
    633	int i, reg_count = DIV_ROUND_UP(plgpio->chip.ngpio, MAX_GPIO_PER_REG);
    634	u32 off;
    635
    636	for (i = 0; i < reg_count; i++) {
    637		off = i * sizeof(int *);
    638
    639		if (plgpio->regs.enb != -1)
    640			regmap_read(plgpio->regmap, plgpio->regs.enb + off,
    641				&plgpio->csave_regs[i].enb);
    642		if (plgpio->regs.eit != -1)
    643			regmap_read(plgpio->regmap, plgpio->regs.eit + off,
    644				&plgpio->csave_regs[i].eit);
    645		regmap_read(plgpio->regmap, plgpio->regs.wdata + off,
    646				&plgpio->csave_regs[i].wdata);
    647		regmap_read(plgpio->regmap, plgpio->regs.dir + off,
    648				&plgpio->csave_regs[i].dir);
    649		regmap_read(plgpio->regmap, plgpio->regs.ie + off,
    650				&plgpio->csave_regs[i].ie);
    651	}
    652
    653	return 0;
    654}
    655
    656/*
    657 * This is used to correct the values in end registers. End registers contain
    658 * extra bits that might be used for other purpose in platform. So, we shouldn't
    659 * overwrite these bits. This macro, reads given register again, preserves other
    660 * bit values (non-plgpio bits), and retain captured value (plgpio bits).
    661 */
    662#define plgpio_prepare_reg(__reg, _off, _mask, _tmp)		\
    663{								\
    664	regmap_read(plgpio->regmap, plgpio->regs.__reg + _off, &_tmp); \
    665	_tmp &= ~_mask;						\
    666	plgpio->csave_regs[i].__reg =				\
    667		_tmp | (plgpio->csave_regs[i].__reg & _mask);	\
    668}
    669
    670static int plgpio_resume(struct device *dev)
    671{
    672	struct plgpio *plgpio = dev_get_drvdata(dev);
    673	int i, reg_count = DIV_ROUND_UP(plgpio->chip.ngpio, MAX_GPIO_PER_REG);
    674	u32 off;
    675	u32 mask, tmp;
    676
    677	for (i = 0; i < reg_count; i++) {
    678		off = i * sizeof(int *);
    679
    680		if (i == reg_count - 1) {
    681			mask = (1 << (plgpio->chip.ngpio - i *
    682						MAX_GPIO_PER_REG)) - 1;
    683
    684			if (plgpio->regs.enb != -1)
    685				plgpio_prepare_reg(enb, off, mask, tmp);
    686
    687			if (plgpio->regs.eit != -1)
    688				plgpio_prepare_reg(eit, off, mask, tmp);
    689
    690			plgpio_prepare_reg(wdata, off, mask, tmp);
    691			plgpio_prepare_reg(dir, off, mask, tmp);
    692			plgpio_prepare_reg(ie, off, mask, tmp);
    693		}
    694
    695		regmap_write(plgpio->regmap, plgpio->regs.wdata + off,
    696			plgpio->csave_regs[i].wdata);
    697
    698		regmap_write(plgpio->regmap, plgpio->regs.dir + off,
    699			plgpio->csave_regs[i].dir);
    700
    701		if (plgpio->regs.eit != -1)
    702			regmap_write(plgpio->regmap, plgpio->regs.eit + off,
    703				plgpio->csave_regs[i].eit);
    704
    705		regmap_write(plgpio->regmap, plgpio->regs.ie + off,
    706			plgpio->csave_regs[i].ie);
    707
    708		if (plgpio->regs.enb != -1)
    709			regmap_write(plgpio->regmap, plgpio->regs.enb + off,
    710				plgpio->csave_regs[i].enb);
    711	}
    712
    713	return 0;
    714}
    715#endif
    716
    717static SIMPLE_DEV_PM_OPS(plgpio_dev_pm_ops, plgpio_suspend, plgpio_resume);
    718
    719static const struct of_device_id plgpio_of_match[] = {
    720	{ .compatible = "st,spear-plgpio" },
    721	{}
    722};
    723
    724static struct platform_driver plgpio_driver = {
    725	.probe = plgpio_probe,
    726	.driver = {
    727		.name = "spear-plgpio",
    728		.pm = &plgpio_dev_pm_ops,
    729		.of_match_table = plgpio_of_match,
    730	},
    731};
    732
    733static int __init plgpio_init(void)
    734{
    735	return platform_driver_register(&plgpio_driver);
    736}
    737subsys_initcall(plgpio_init);