1 // SPDX-License-Identifier: GPL-2.0+
2 //
3 // Exynos specific support for Samsung pinctrl/gpiolib driver with eint support.
4 //
5 // Copyright (c) 2012 Samsung Electronics Co., Ltd.
6 // http://www.samsung.com
7 // Copyright (c) 2012 Linaro Ltd
8 // http://www.linaro.org
9 //
10 // Author: Thomas Abraham <thomas.ab@samsung.com>
11 //
12 // This file contains the Samsung Exynos specific information required by the
13 // the Samsung pinctrl/gpiolib driver. It also includes the implementation of
14 // external gpio and wakeup interrupt support.
15
16 #include <linux/clk.h>
17 #include <linux/device.h>
18 #include <linux/interrupt.h>
19 #include <linux/irqdomain.h>
20 #include <linux/irq.h>
21 #include <linux/irqchip/chained_irq.h>
22 #include <linux/of.h>
23 #include <linux/of_irq.h>
24 #include <linux/slab.h>
25 #include <linux/spinlock.h>
26 #include <linux/regmap.h>
27 #include <linux/err.h>
28 #include <linux/soc/samsung/exynos-pmu.h>
29 #include <linux/soc/samsung/exynos-regs-pmu.h>
30
31 #include "pinctrl-samsung.h"
32 #include "pinctrl-exynos.h"
33
34 struct exynos_irq_chip {
35 struct irq_chip chip;
36
37 u32 eint_con;
38 u32 eint_mask;
39 u32 eint_pend;
40 u32 *eint_wake_mask_value;
41 u32 eint_wake_mask_reg;
42 void (*set_eint_wakeup_mask)(struct samsung_pinctrl_drv_data *drvdata,
43 struct exynos_irq_chip *irq_chip);
44 };
45
to_exynos_irq_chip(struct irq_chip * chip)46 static inline struct exynos_irq_chip *to_exynos_irq_chip(struct irq_chip *chip)
47 {
48 return container_of(chip, struct exynos_irq_chip, chip);
49 }
50
exynos_irq_mask(struct irq_data * irqd)51 static void exynos_irq_mask(struct irq_data *irqd)
52 {
53 struct irq_chip *chip = irq_data_get_irq_chip(irqd);
54 struct exynos_irq_chip *our_chip = to_exynos_irq_chip(chip);
55 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
56 unsigned long reg_mask;
57 unsigned int mask;
58 unsigned long flags;
59
60 if (bank->eint_mask_offset)
61 reg_mask = bank->pctl_offset + bank->eint_mask_offset;
62 else
63 reg_mask = our_chip->eint_mask + bank->eint_offset;
64
65 if (clk_enable(bank->drvdata->pclk)) {
66 dev_err(bank->gpio_chip.parent,
67 "unable to enable clock for masking IRQ\n");
68 return;
69 }
70
71 raw_spin_lock_irqsave(&bank->slock, flags);
72
73 mask = readl(bank->eint_base + reg_mask);
74 mask |= 1 << irqd->hwirq;
75 writel(mask, bank->eint_base + reg_mask);
76
77 raw_spin_unlock_irqrestore(&bank->slock, flags);
78
79 clk_disable(bank->drvdata->pclk);
80 }
81
exynos_irq_ack(struct irq_data * irqd)82 static void exynos_irq_ack(struct irq_data *irqd)
83 {
84 struct irq_chip *chip = irq_data_get_irq_chip(irqd);
85 struct exynos_irq_chip *our_chip = to_exynos_irq_chip(chip);
86 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
87 unsigned long reg_pend;
88
89 if (bank->eint_pend_offset)
90 reg_pend = bank->pctl_offset + bank->eint_pend_offset;
91 else
92 reg_pend = our_chip->eint_pend + bank->eint_offset;
93
94 if (clk_enable(bank->drvdata->pclk)) {
95 dev_err(bank->gpio_chip.parent,
96 "unable to enable clock to ack IRQ\n");
97 return;
98 }
99
100 writel(1 << irqd->hwirq, bank->eint_base + reg_pend);
101
102 clk_disable(bank->drvdata->pclk);
103 }
104
exynos_irq_unmask(struct irq_data * irqd)105 static void exynos_irq_unmask(struct irq_data *irqd)
106 {
107 struct irq_chip *chip = irq_data_get_irq_chip(irqd);
108 struct exynos_irq_chip *our_chip = to_exynos_irq_chip(chip);
109 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
110 unsigned long reg_mask;
111 unsigned int mask;
112 unsigned long flags;
113
114 /*
115 * Ack level interrupts right before unmask
116 *
117 * If we don't do this we'll get a double-interrupt. Level triggered
118 * interrupts must not fire an interrupt if the level is not
119 * _currently_ active, even if it was active while the interrupt was
120 * masked.
121 */
122 if (irqd_get_trigger_type(irqd) & IRQ_TYPE_LEVEL_MASK)
123 exynos_irq_ack(irqd);
124
125 if (bank->eint_mask_offset)
126 reg_mask = bank->pctl_offset + bank->eint_mask_offset;
127 else
128 reg_mask = our_chip->eint_mask + bank->eint_offset;
129
130 if (clk_enable(bank->drvdata->pclk)) {
131 dev_err(bank->gpio_chip.parent,
132 "unable to enable clock for unmasking IRQ\n");
133 return;
134 }
135
136 raw_spin_lock_irqsave(&bank->slock, flags);
137
138 mask = readl(bank->eint_base + reg_mask);
139 mask &= ~(1 << irqd->hwirq);
140 writel(mask, bank->eint_base + reg_mask);
141
142 raw_spin_unlock_irqrestore(&bank->slock, flags);
143
144 clk_disable(bank->drvdata->pclk);
145 }
146
exynos_irq_set_type(struct irq_data * irqd,unsigned int type)147 static int exynos_irq_set_type(struct irq_data *irqd, unsigned int type)
148 {
149 struct irq_chip *chip = irq_data_get_irq_chip(irqd);
150 struct exynos_irq_chip *our_chip = to_exynos_irq_chip(chip);
151 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
152 unsigned int shift = EXYNOS_EINT_CON_LEN * irqd->hwirq;
153 unsigned int con, trig_type;
154 unsigned long reg_con;
155 int ret;
156
157 switch (type) {
158 case IRQ_TYPE_EDGE_RISING:
159 trig_type = EXYNOS_EINT_EDGE_RISING;
160 break;
161 case IRQ_TYPE_EDGE_FALLING:
162 trig_type = EXYNOS_EINT_EDGE_FALLING;
163 break;
164 case IRQ_TYPE_EDGE_BOTH:
165 trig_type = EXYNOS_EINT_EDGE_BOTH;
166 break;
167 case IRQ_TYPE_LEVEL_HIGH:
168 trig_type = EXYNOS_EINT_LEVEL_HIGH;
169 break;
170 case IRQ_TYPE_LEVEL_LOW:
171 trig_type = EXYNOS_EINT_LEVEL_LOW;
172 break;
173 default:
174 pr_err("unsupported external interrupt type\n");
175 return -EINVAL;
176 }
177
178 if (type & IRQ_TYPE_EDGE_BOTH)
179 irq_set_handler_locked(irqd, handle_edge_irq);
180 else
181 irq_set_handler_locked(irqd, handle_level_irq);
182
183 if (bank->eint_con_offset)
184 reg_con = bank->pctl_offset + bank->eint_con_offset;
185 else
186 reg_con = our_chip->eint_con + bank->eint_offset;
187
188 ret = clk_enable(bank->drvdata->pclk);
189 if (ret) {
190 dev_err(bank->gpio_chip.parent,
191 "unable to enable clock for configuring IRQ type\n");
192 return ret;
193 }
194
195 con = readl(bank->eint_base + reg_con);
196 con &= ~(EXYNOS_EINT_CON_MASK << shift);
197 con |= trig_type << shift;
198 writel(con, bank->eint_base + reg_con);
199
200 clk_disable(bank->drvdata->pclk);
201
202 return 0;
203 }
204
exynos_irq_set_affinity(struct irq_data * irqd,const struct cpumask * dest,bool force)205 static int exynos_irq_set_affinity(struct irq_data *irqd,
206 const struct cpumask *dest, bool force)
207 {
208 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
209 struct samsung_pinctrl_drv_data *d = bank->drvdata;
210 struct irq_data *parent = irq_get_irq_data(d->irq);
211
212 if (parent)
213 return parent->chip->irq_set_affinity(parent, dest, force);
214
215 return -EINVAL;
216 }
217
exynos_irq_request_resources(struct irq_data * irqd)218 static int exynos_irq_request_resources(struct irq_data *irqd)
219 {
220 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
221 const struct samsung_pin_bank_type *bank_type = bank->type;
222 unsigned long reg_con, flags;
223 unsigned int shift, mask, con;
224 int ret;
225
226 ret = gpiochip_lock_as_irq(&bank->gpio_chip, irqd->hwirq);
227 if (ret) {
228 dev_err(bank->gpio_chip.parent,
229 "unable to lock pin %s-%lu IRQ\n",
230 bank->name, irqd->hwirq);
231 return ret;
232 }
233
234 reg_con = bank->pctl_offset + bank_type->reg_offset[PINCFG_TYPE_FUNC];
235 shift = irqd->hwirq * bank_type->fld_width[PINCFG_TYPE_FUNC];
236 mask = (1 << bank_type->fld_width[PINCFG_TYPE_FUNC]) - 1;
237
238 ret = clk_enable(bank->drvdata->pclk);
239 if (ret) {
240 dev_err(bank->gpio_chip.parent,
241 "unable to enable clock for configuring pin %s-%lu\n",
242 bank->name, irqd->hwirq);
243 return ret;
244 }
245
246 raw_spin_lock_irqsave(&bank->slock, flags);
247
248 con = readl(bank->pctl_base + reg_con);
249 con &= ~(mask << shift);
250 con |= EXYNOS_PIN_CON_FUNC_EINT << shift;
251 writel(con, bank->pctl_base + reg_con);
252
253 raw_spin_unlock_irqrestore(&bank->slock, flags);
254
255 clk_disable(bank->drvdata->pclk);
256
257 return 0;
258 }
259
exynos_irq_release_resources(struct irq_data * irqd)260 static void exynos_irq_release_resources(struct irq_data *irqd)
261 {
262 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
263 const struct samsung_pin_bank_type *bank_type = bank->type;
264 unsigned long reg_con, flags;
265 unsigned int shift, mask, con;
266
267 reg_con = bank->pctl_offset + bank_type->reg_offset[PINCFG_TYPE_FUNC];
268 shift = irqd->hwirq * bank_type->fld_width[PINCFG_TYPE_FUNC];
269 mask = (1 << bank_type->fld_width[PINCFG_TYPE_FUNC]) - 1;
270
271 if (clk_enable(bank->drvdata->pclk)) {
272 dev_err(bank->gpio_chip.parent,
273 "unable to enable clock for deconfiguring pin %s-%lu\n",
274 bank->name, irqd->hwirq);
275 return;
276 }
277
278 raw_spin_lock_irqsave(&bank->slock, flags);
279
280 con = readl(bank->pctl_base + reg_con);
281 con &= ~(mask << shift);
282 con |= PIN_CON_FUNC_INPUT << shift;
283 writel(con, bank->pctl_base + reg_con);
284
285 raw_spin_unlock_irqrestore(&bank->slock, flags);
286
287 clk_disable(bank->drvdata->pclk);
288
289 gpiochip_unlock_as_irq(&bank->gpio_chip, irqd->hwirq);
290 }
291
292 /*
293 * irq_chip for gpio interrupts.
294 */
295 static const struct exynos_irq_chip exynos_gpio_irq_chip __initconst = {
296 .chip = {
297 .name = "exynos_gpio_irq_chip",
298 .irq_unmask = exynos_irq_unmask,
299 .irq_mask = exynos_irq_mask,
300 .irq_ack = exynos_irq_ack,
301 .irq_set_type = exynos_irq_set_type,
302 .irq_set_affinity = exynos_irq_set_affinity,
303 .irq_request_resources = exynos_irq_request_resources,
304 .irq_release_resources = exynos_irq_release_resources,
305 },
306 .eint_con = EXYNOS_GPIO_ECON_OFFSET,
307 .eint_mask = EXYNOS_GPIO_EMASK_OFFSET,
308 .eint_pend = EXYNOS_GPIO_EPEND_OFFSET,
309 /* eint_wake_mask_value not used */
310 };
311
exynos_eint_irq_map(struct irq_domain * h,unsigned int virq,irq_hw_number_t hw)312 static int exynos_eint_irq_map(struct irq_domain *h, unsigned int virq,
313 irq_hw_number_t hw)
314 {
315 struct samsung_pin_bank *b = h->host_data;
316
317 irq_set_chip_data(virq, b);
318 irq_set_chip_and_handler(virq, &b->irq_chip->chip,
319 handle_level_irq);
320 return 0;
321 }
322
323 /*
324 * irq domain callbacks for external gpio and wakeup interrupt controllers.
325 */
326 static const struct irq_domain_ops exynos_eint_irqd_ops = {
327 .map = exynos_eint_irq_map,
328 .xlate = irq_domain_xlate_twocell,
329 };
330
exynos_eint_gpio_irq(int irq,void * data)331 static irqreturn_t exynos_eint_gpio_irq(int irq, void *data)
332 {
333 struct samsung_pinctrl_drv_data *d = data;
334 struct samsung_pin_bank *bank = d->pin_banks;
335 unsigned int svc, group, pin;
336 int ret;
337
338 if (clk_enable(bank->drvdata->pclk)) {
339 dev_err(bank->gpio_chip.parent,
340 "unable to enable clock for handling IRQ\n");
341 return IRQ_NONE;
342 }
343
344 if (bank->eint_con_offset)
345 svc = readl(bank->eint_base + EXYNOSAUTO_SVC_OFFSET);
346 else
347 svc = readl(bank->eint_base + EXYNOS_SVC_OFFSET);
348
349 clk_disable(bank->drvdata->pclk);
350
351 group = EXYNOS_SVC_GROUP(svc);
352 pin = svc & EXYNOS_SVC_NUM_MASK;
353
354 if (!group)
355 return IRQ_HANDLED;
356 bank += (group - 1);
357
358 ret = generic_handle_domain_irq(bank->irq_domain, pin);
359 if (ret)
360 return IRQ_NONE;
361
362 return IRQ_HANDLED;
363 }
364
365 struct exynos_eint_gpio_save {
366 u32 eint_con;
367 u32 eint_fltcon0;
368 u32 eint_fltcon1;
369 u32 eint_mask;
370 };
371
372 /*
373 * exynos_eint_gpio_init() - setup handling of external gpio interrupts.
374 * @d: driver data of samsung pinctrl driver.
375 */
exynos_eint_gpio_init(struct samsung_pinctrl_drv_data * d)376 __init int exynos_eint_gpio_init(struct samsung_pinctrl_drv_data *d)
377 {
378 struct samsung_pin_bank *bank;
379 struct device *dev = d->dev;
380 int ret;
381 int i;
382
383 if (!d->irq) {
384 dev_err(dev, "irq number not available\n");
385 return -EINVAL;
386 }
387
388 ret = devm_request_irq(dev, d->irq, exynos_eint_gpio_irq,
389 0, dev_name(dev), d);
390 if (ret) {
391 dev_err(dev, "irq request failed\n");
392 return -ENXIO;
393 }
394
395 bank = d->pin_banks;
396 for (i = 0; i < d->nr_banks; ++i, ++bank) {
397 if (bank->eint_type != EINT_TYPE_GPIO)
398 continue;
399
400 bank->irq_chip = devm_kmemdup(dev, &exynos_gpio_irq_chip,
401 sizeof(*bank->irq_chip), GFP_KERNEL);
402 if (!bank->irq_chip) {
403 ret = -ENOMEM;
404 goto err_domains;
405 }
406 bank->irq_chip->chip.name = bank->name;
407
408 bank->irq_domain = irq_domain_create_linear(bank->fwnode,
409 bank->nr_pins, &exynos_eint_irqd_ops, bank);
410 if (!bank->irq_domain) {
411 dev_err(dev, "gpio irq domain add failed\n");
412 ret = -ENXIO;
413 goto err_domains;
414 }
415
416 bank->soc_priv = devm_kzalloc(d->dev,
417 sizeof(struct exynos_eint_gpio_save), GFP_KERNEL);
418 if (!bank->soc_priv) {
419 irq_domain_remove(bank->irq_domain);
420 ret = -ENOMEM;
421 goto err_domains;
422 }
423
424 }
425
426 return 0;
427
428 err_domains:
429 for (--i, --bank; i >= 0; --i, --bank) {
430 if (bank->eint_type != EINT_TYPE_GPIO)
431 continue;
432 irq_domain_remove(bank->irq_domain);
433 }
434
435 return ret;
436 }
437
exynos_wkup_irq_set_wake(struct irq_data * irqd,unsigned int on)438 static int exynos_wkup_irq_set_wake(struct irq_data *irqd, unsigned int on)
439 {
440 struct irq_chip *chip = irq_data_get_irq_chip(irqd);
441 struct exynos_irq_chip *our_chip = to_exynos_irq_chip(chip);
442 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
443 unsigned long bit = 1UL << (2 * bank->eint_offset + irqd->hwirq);
444
445 pr_info("wake %s for irq %u (%s-%lu)\n", on ? "enabled" : "disabled",
446 irqd->irq, bank->name, irqd->hwirq);
447
448 if (!on)
449 *our_chip->eint_wake_mask_value |= bit;
450 else
451 *our_chip->eint_wake_mask_value &= ~bit;
452
453 return 0;
454 }
455
456 static void
exynos_pinctrl_set_eint_wakeup_mask(struct samsung_pinctrl_drv_data * drvdata,struct exynos_irq_chip * irq_chip)457 exynos_pinctrl_set_eint_wakeup_mask(struct samsung_pinctrl_drv_data *drvdata,
458 struct exynos_irq_chip *irq_chip)
459 {
460 struct regmap *pmu_regs;
461
462 if (!drvdata->retention_ctrl || !drvdata->retention_ctrl->priv) {
463 dev_warn(drvdata->dev,
464 "No retention data configured bank with external wakeup interrupt. Wake-up mask will not be set.\n");
465 return;
466 }
467
468 pmu_regs = drvdata->retention_ctrl->priv;
469 dev_info(drvdata->dev,
470 "Setting external wakeup interrupt mask: 0x%x\n",
471 *irq_chip->eint_wake_mask_value);
472
473 regmap_write(pmu_regs, irq_chip->eint_wake_mask_reg,
474 *irq_chip->eint_wake_mask_value);
475 }
476
477 static void
s5pv210_pinctrl_set_eint_wakeup_mask(struct samsung_pinctrl_drv_data * drvdata,struct exynos_irq_chip * irq_chip)478 s5pv210_pinctrl_set_eint_wakeup_mask(struct samsung_pinctrl_drv_data *drvdata,
479 struct exynos_irq_chip *irq_chip)
480
481 {
482 void __iomem *clk_base;
483
484 if (!drvdata->retention_ctrl || !drvdata->retention_ctrl->priv) {
485 dev_warn(drvdata->dev,
486 "No retention data configured bank with external wakeup interrupt. Wake-up mask will not be set.\n");
487 return;
488 }
489
490
491 clk_base = (void __iomem *) drvdata->retention_ctrl->priv;
492
493 __raw_writel(*irq_chip->eint_wake_mask_value,
494 clk_base + irq_chip->eint_wake_mask_reg);
495 }
496
497 static u32 eint_wake_mask_value = EXYNOS_EINT_WAKEUP_MASK_DISABLED;
498 /*
499 * irq_chip for wakeup interrupts
500 */
501 static const struct exynos_irq_chip s5pv210_wkup_irq_chip __initconst = {
502 .chip = {
503 .name = "s5pv210_wkup_irq_chip",
504 .irq_unmask = exynos_irq_unmask,
505 .irq_mask = exynos_irq_mask,
506 .irq_ack = exynos_irq_ack,
507 .irq_set_type = exynos_irq_set_type,
508 .irq_set_wake = exynos_wkup_irq_set_wake,
509 .irq_request_resources = exynos_irq_request_resources,
510 .irq_release_resources = exynos_irq_release_resources,
511 },
512 .eint_con = EXYNOS_WKUP_ECON_OFFSET,
513 .eint_mask = EXYNOS_WKUP_EMASK_OFFSET,
514 .eint_pend = EXYNOS_WKUP_EPEND_OFFSET,
515 .eint_wake_mask_value = &eint_wake_mask_value,
516 /* Only differences with exynos4210_wkup_irq_chip: */
517 .eint_wake_mask_reg = S5PV210_EINT_WAKEUP_MASK,
518 .set_eint_wakeup_mask = s5pv210_pinctrl_set_eint_wakeup_mask,
519 };
520
521 static const struct exynos_irq_chip exynos4210_wkup_irq_chip __initconst = {
522 .chip = {
523 .name = "exynos4210_wkup_irq_chip",
524 .irq_unmask = exynos_irq_unmask,
525 .irq_mask = exynos_irq_mask,
526 .irq_ack = exynos_irq_ack,
527 .irq_set_type = exynos_irq_set_type,
528 .irq_set_wake = exynos_wkup_irq_set_wake,
529 .irq_request_resources = exynos_irq_request_resources,
530 .irq_release_resources = exynos_irq_release_resources,
531 },
532 .eint_con = EXYNOS_WKUP_ECON_OFFSET,
533 .eint_mask = EXYNOS_WKUP_EMASK_OFFSET,
534 .eint_pend = EXYNOS_WKUP_EPEND_OFFSET,
535 .eint_wake_mask_value = &eint_wake_mask_value,
536 .eint_wake_mask_reg = EXYNOS_EINT_WAKEUP_MASK,
537 .set_eint_wakeup_mask = exynos_pinctrl_set_eint_wakeup_mask,
538 };
539
540 static const struct exynos_irq_chip exynos7_wkup_irq_chip __initconst = {
541 .chip = {
542 .name = "exynos7_wkup_irq_chip",
543 .irq_unmask = exynos_irq_unmask,
544 .irq_mask = exynos_irq_mask,
545 .irq_ack = exynos_irq_ack,
546 .irq_set_type = exynos_irq_set_type,
547 .irq_set_wake = exynos_wkup_irq_set_wake,
548 .irq_request_resources = exynos_irq_request_resources,
549 .irq_release_resources = exynos_irq_release_resources,
550 },
551 .eint_con = EXYNOS7_WKUP_ECON_OFFSET,
552 .eint_mask = EXYNOS7_WKUP_EMASK_OFFSET,
553 .eint_pend = EXYNOS7_WKUP_EPEND_OFFSET,
554 .eint_wake_mask_value = &eint_wake_mask_value,
555 .eint_wake_mask_reg = EXYNOS5433_EINT_WAKEUP_MASK,
556 .set_eint_wakeup_mask = exynos_pinctrl_set_eint_wakeup_mask,
557 };
558
559 static const struct exynos_irq_chip exynosautov920_wkup_irq_chip __initconst = {
560 .chip = {
561 .name = "exynosautov920_wkup_irq_chip",
562 .irq_unmask = exynos_irq_unmask,
563 .irq_mask = exynos_irq_mask,
564 .irq_ack = exynos_irq_ack,
565 .irq_set_type = exynos_irq_set_type,
566 .irq_set_wake = exynos_wkup_irq_set_wake,
567 .irq_request_resources = exynos_irq_request_resources,
568 .irq_release_resources = exynos_irq_release_resources,
569 },
570 .eint_wake_mask_value = &eint_wake_mask_value,
571 .eint_wake_mask_reg = EXYNOS5433_EINT_WAKEUP_MASK,
572 .set_eint_wakeup_mask = exynos_pinctrl_set_eint_wakeup_mask,
573 };
574
575 /* list of external wakeup controllers supported */
576 static const struct of_device_id exynos_wkup_irq_ids[] = {
577 { .compatible = "samsung,s5pv210-wakeup-eint",
578 .data = &s5pv210_wkup_irq_chip },
579 { .compatible = "samsung,exynos4210-wakeup-eint",
580 .data = &exynos4210_wkup_irq_chip },
581 { .compatible = "samsung,exynos7-wakeup-eint",
582 .data = &exynos7_wkup_irq_chip },
583 { .compatible = "samsung,exynos850-wakeup-eint",
584 .data = &exynos7_wkup_irq_chip },
585 { .compatible = "samsung,exynosautov9-wakeup-eint",
586 .data = &exynos7_wkup_irq_chip },
587 { .compatible = "samsung,exynosautov920-wakeup-eint",
588 .data = &exynosautov920_wkup_irq_chip },
589 { }
590 };
591
592 /* interrupt handler for wakeup interrupts 0..15 */
exynos_irq_eint0_15(struct irq_desc * desc)593 static void exynos_irq_eint0_15(struct irq_desc *desc)
594 {
595 struct exynos_weint_data *eintd = irq_desc_get_handler_data(desc);
596 struct samsung_pin_bank *bank = eintd->bank;
597 struct irq_chip *chip = irq_desc_get_chip(desc);
598
599 chained_irq_enter(chip, desc);
600
601 generic_handle_domain_irq(bank->irq_domain, eintd->irq);
602
603 chained_irq_exit(chip, desc);
604 }
605
exynos_irq_demux_eint(unsigned int pend,struct irq_domain * domain)606 static inline void exynos_irq_demux_eint(unsigned int pend,
607 struct irq_domain *domain)
608 {
609 unsigned int irq;
610
611 while (pend) {
612 irq = fls(pend) - 1;
613 generic_handle_domain_irq(domain, irq);
614 pend &= ~(1 << irq);
615 }
616 }
617
618 /* interrupt handler for wakeup interrupt 16 */
exynos_irq_demux_eint16_31(struct irq_desc * desc)619 static void exynos_irq_demux_eint16_31(struct irq_desc *desc)
620 {
621 struct irq_chip *chip = irq_desc_get_chip(desc);
622 struct exynos_muxed_weint_data *eintd = irq_desc_get_handler_data(desc);
623 unsigned int pend;
624 unsigned int mask;
625 int i;
626
627 chained_irq_enter(chip, desc);
628
629 /*
630 * just enable the clock once here, to avoid an enable/disable dance for
631 * each bank.
632 */
633 if (eintd->nr_banks) {
634 struct samsung_pin_bank *b = eintd->banks[0];
635
636 if (clk_enable(b->drvdata->pclk)) {
637 dev_err(b->gpio_chip.parent,
638 "unable to enable clock for pending IRQs\n");
639 return;
640 }
641 }
642
643 for (i = 0; i < eintd->nr_banks; ++i) {
644 struct samsung_pin_bank *b = eintd->banks[i];
645 pend = readl(b->eint_base + b->irq_chip->eint_pend
646 + b->eint_offset);
647 mask = readl(b->eint_base + b->irq_chip->eint_mask
648 + b->eint_offset);
649 exynos_irq_demux_eint(pend & ~mask, b->irq_domain);
650 }
651
652 if (eintd->nr_banks)
653 clk_disable(eintd->banks[0]->drvdata->pclk);
654
655 chained_irq_exit(chip, desc);
656 }
657
658 /*
659 * exynos_eint_wkup_init() - setup handling of external wakeup interrupts.
660 * @d: driver data of samsung pinctrl driver.
661 */
exynos_eint_wkup_init(struct samsung_pinctrl_drv_data * d)662 __init int exynos_eint_wkup_init(struct samsung_pinctrl_drv_data *d)
663 {
664 struct device *dev = d->dev;
665 struct device_node *wkup_np __free(device_node) = NULL;
666 struct device_node *np;
667 struct samsung_pin_bank *bank;
668 struct exynos_weint_data *weint_data;
669 struct exynos_muxed_weint_data *muxed_data;
670 const struct exynos_irq_chip *irq_chip;
671 unsigned int muxed_banks = 0;
672 unsigned int i;
673 int idx, irq;
674
675 for_each_child_of_node(dev->of_node, np) {
676 const struct of_device_id *match;
677
678 match = of_match_node(exynos_wkup_irq_ids, np);
679 if (match) {
680 irq_chip = match->data;
681 wkup_np = np;
682 break;
683 }
684 }
685 if (!wkup_np)
686 return -ENODEV;
687
688 bank = d->pin_banks;
689 for (i = 0; i < d->nr_banks; ++i, ++bank) {
690 if (bank->eint_type != EINT_TYPE_WKUP)
691 continue;
692
693 bank->irq_chip = devm_kmemdup(dev, irq_chip, sizeof(*irq_chip),
694 GFP_KERNEL);
695 if (!bank->irq_chip)
696 return -ENOMEM;
697 bank->irq_chip->chip.name = bank->name;
698
699 bank->irq_domain = irq_domain_create_linear(bank->fwnode,
700 bank->nr_pins, &exynos_eint_irqd_ops, bank);
701 if (!bank->irq_domain) {
702 dev_err(dev, "wkup irq domain add failed\n");
703 return -ENXIO;
704 }
705
706 if (!fwnode_property_present(bank->fwnode, "interrupts")) {
707 bank->eint_type = EINT_TYPE_WKUP_MUX;
708 ++muxed_banks;
709 continue;
710 }
711
712 weint_data = devm_kcalloc(dev,
713 bank->nr_pins, sizeof(*weint_data),
714 GFP_KERNEL);
715 if (!weint_data)
716 return -ENOMEM;
717
718 for (idx = 0; idx < bank->nr_pins; ++idx) {
719 irq = irq_of_parse_and_map(to_of_node(bank->fwnode), idx);
720 if (!irq) {
721 dev_err(dev, "irq number for eint-%s-%d not found\n",
722 bank->name, idx);
723 continue;
724 }
725 weint_data[idx].irq = idx;
726 weint_data[idx].bank = bank;
727 irq_set_chained_handler_and_data(irq,
728 exynos_irq_eint0_15,
729 &weint_data[idx]);
730 }
731 }
732
733 if (!muxed_banks)
734 return 0;
735
736 irq = irq_of_parse_and_map(wkup_np, 0);
737 if (!irq) {
738 dev_err(dev, "irq number for muxed EINTs not found\n");
739 return 0;
740 }
741
742 muxed_data = devm_kzalloc(dev, sizeof(*muxed_data)
743 + muxed_banks*sizeof(struct samsung_pin_bank *), GFP_KERNEL);
744 if (!muxed_data)
745 return -ENOMEM;
746 muxed_data->nr_banks = muxed_banks;
747
748 irq_set_chained_handler_and_data(irq, exynos_irq_demux_eint16_31,
749 muxed_data);
750
751 bank = d->pin_banks;
752 idx = 0;
753 for (i = 0; i < d->nr_banks; ++i, ++bank) {
754 if (bank->eint_type != EINT_TYPE_WKUP_MUX)
755 continue;
756
757 muxed_data->banks[idx++] = bank;
758 }
759
760 return 0;
761 }
762
exynos_pinctrl_suspend_bank(struct samsung_pinctrl_drv_data * drvdata,struct samsung_pin_bank * bank)763 static void exynos_pinctrl_suspend_bank(
764 struct samsung_pinctrl_drv_data *drvdata,
765 struct samsung_pin_bank *bank)
766 {
767 struct exynos_eint_gpio_save *save = bank->soc_priv;
768 const void __iomem *regs = bank->eint_base;
769
770 if (clk_enable(bank->drvdata->pclk)) {
771 dev_err(bank->gpio_chip.parent,
772 "unable to enable clock for saving state\n");
773 return;
774 }
775
776 save->eint_con = readl(regs + EXYNOS_GPIO_ECON_OFFSET
777 + bank->eint_offset);
778 save->eint_fltcon0 = readl(regs + EXYNOS_GPIO_EFLTCON_OFFSET
779 + 2 * bank->eint_offset);
780 save->eint_fltcon1 = readl(regs + EXYNOS_GPIO_EFLTCON_OFFSET
781 + 2 * bank->eint_offset + 4);
782 save->eint_mask = readl(regs + bank->irq_chip->eint_mask
783 + bank->eint_offset);
784
785 clk_disable(bank->drvdata->pclk);
786
787 pr_debug("%s: save con %#010x\n", bank->name, save->eint_con);
788 pr_debug("%s: save fltcon0 %#010x\n", bank->name, save->eint_fltcon0);
789 pr_debug("%s: save fltcon1 %#010x\n", bank->name, save->eint_fltcon1);
790 pr_debug("%s: save mask %#010x\n", bank->name, save->eint_mask);
791 }
792
exynosauto_pinctrl_suspend_bank(struct samsung_pinctrl_drv_data * drvdata,struct samsung_pin_bank * bank)793 static void exynosauto_pinctrl_suspend_bank(struct samsung_pinctrl_drv_data *drvdata,
794 struct samsung_pin_bank *bank)
795 {
796 struct exynos_eint_gpio_save *save = bank->soc_priv;
797 const void __iomem *regs = bank->eint_base;
798
799 if (clk_enable(bank->drvdata->pclk)) {
800 dev_err(bank->gpio_chip.parent,
801 "unable to enable clock for saving state\n");
802 return;
803 }
804
805 save->eint_con = readl(regs + bank->pctl_offset + bank->eint_con_offset);
806 save->eint_mask = readl(regs + bank->pctl_offset + bank->eint_mask_offset);
807
808 clk_disable(bank->drvdata->pclk);
809
810 pr_debug("%s: save con %#010x\n", bank->name, save->eint_con);
811 pr_debug("%s: save mask %#010x\n", bank->name, save->eint_mask);
812 }
813
exynos_pinctrl_suspend(struct samsung_pinctrl_drv_data * drvdata)814 void exynos_pinctrl_suspend(struct samsung_pinctrl_drv_data *drvdata)
815 {
816 struct samsung_pin_bank *bank = drvdata->pin_banks;
817 struct exynos_irq_chip *irq_chip = NULL;
818 int i;
819
820 for (i = 0; i < drvdata->nr_banks; ++i, ++bank) {
821 if (bank->eint_type == EINT_TYPE_GPIO) {
822 if (bank->eint_con_offset)
823 exynosauto_pinctrl_suspend_bank(drvdata, bank);
824 else
825 exynos_pinctrl_suspend_bank(drvdata, bank);
826 }
827 else if (bank->eint_type == EINT_TYPE_WKUP) {
828 if (!irq_chip) {
829 irq_chip = bank->irq_chip;
830 irq_chip->set_eint_wakeup_mask(drvdata,
831 irq_chip);
832 }
833 }
834 }
835 }
836
exynos_pinctrl_resume_bank(struct samsung_pinctrl_drv_data * drvdata,struct samsung_pin_bank * bank)837 static void exynos_pinctrl_resume_bank(
838 struct samsung_pinctrl_drv_data *drvdata,
839 struct samsung_pin_bank *bank)
840 {
841 struct exynos_eint_gpio_save *save = bank->soc_priv;
842 void __iomem *regs = bank->eint_base;
843
844 if (clk_enable(bank->drvdata->pclk)) {
845 dev_err(bank->gpio_chip.parent,
846 "unable to enable clock for restoring state\n");
847 return;
848 }
849
850 pr_debug("%s: con %#010x => %#010x\n", bank->name,
851 readl(regs + EXYNOS_GPIO_ECON_OFFSET
852 + bank->eint_offset), save->eint_con);
853 pr_debug("%s: fltcon0 %#010x => %#010x\n", bank->name,
854 readl(regs + EXYNOS_GPIO_EFLTCON_OFFSET
855 + 2 * bank->eint_offset), save->eint_fltcon0);
856 pr_debug("%s: fltcon1 %#010x => %#010x\n", bank->name,
857 readl(regs + EXYNOS_GPIO_EFLTCON_OFFSET
858 + 2 * bank->eint_offset + 4), save->eint_fltcon1);
859 pr_debug("%s: mask %#010x => %#010x\n", bank->name,
860 readl(regs + bank->irq_chip->eint_mask
861 + bank->eint_offset), save->eint_mask);
862
863 writel(save->eint_con, regs + EXYNOS_GPIO_ECON_OFFSET
864 + bank->eint_offset);
865 writel(save->eint_fltcon0, regs + EXYNOS_GPIO_EFLTCON_OFFSET
866 + 2 * bank->eint_offset);
867 writel(save->eint_fltcon1, regs + EXYNOS_GPIO_EFLTCON_OFFSET
868 + 2 * bank->eint_offset + 4);
869 writel(save->eint_mask, regs + bank->irq_chip->eint_mask
870 + bank->eint_offset);
871
872 clk_disable(bank->drvdata->pclk);
873 }
874
exynosauto_pinctrl_resume_bank(struct samsung_pinctrl_drv_data * drvdata,struct samsung_pin_bank * bank)875 static void exynosauto_pinctrl_resume_bank(struct samsung_pinctrl_drv_data *drvdata,
876 struct samsung_pin_bank *bank)
877 {
878 struct exynos_eint_gpio_save *save = bank->soc_priv;
879 void __iomem *regs = bank->eint_base;
880
881 if (clk_enable(bank->drvdata->pclk)) {
882 dev_err(bank->gpio_chip.parent,
883 "unable to enable clock for restoring state\n");
884 return;
885 }
886
887 pr_debug("%s: con %#010x => %#010x\n", bank->name,
888 readl(regs + bank->pctl_offset + bank->eint_con_offset), save->eint_con);
889 pr_debug("%s: mask %#010x => %#010x\n", bank->name,
890 readl(regs + bank->pctl_offset + bank->eint_mask_offset), save->eint_mask);
891
892 writel(save->eint_con, regs + bank->pctl_offset + bank->eint_con_offset);
893 writel(save->eint_mask, regs + bank->pctl_offset + bank->eint_mask_offset);
894
895 clk_disable(bank->drvdata->pclk);
896 }
897
exynos_pinctrl_resume(struct samsung_pinctrl_drv_data * drvdata)898 void exynos_pinctrl_resume(struct samsung_pinctrl_drv_data *drvdata)
899 {
900 struct samsung_pin_bank *bank = drvdata->pin_banks;
901 int i;
902
903 for (i = 0; i < drvdata->nr_banks; ++i, ++bank)
904 if (bank->eint_type == EINT_TYPE_GPIO) {
905 if (bank->eint_con_offset)
906 exynosauto_pinctrl_resume_bank(drvdata, bank);
907 else
908 exynos_pinctrl_resume_bank(drvdata, bank);
909 }
910 }
911
exynos_retention_enable(struct samsung_pinctrl_drv_data * drvdata)912 static void exynos_retention_enable(struct samsung_pinctrl_drv_data *drvdata)
913 {
914 if (drvdata->retention_ctrl->refcnt)
915 atomic_inc(drvdata->retention_ctrl->refcnt);
916 }
917
exynos_retention_disable(struct samsung_pinctrl_drv_data * drvdata)918 static void exynos_retention_disable(struct samsung_pinctrl_drv_data *drvdata)
919 {
920 struct samsung_retention_ctrl *ctrl = drvdata->retention_ctrl;
921 struct regmap *pmu_regs = ctrl->priv;
922 int i;
923
924 if (ctrl->refcnt && !atomic_dec_and_test(ctrl->refcnt))
925 return;
926
927 for (i = 0; i < ctrl->nr_regs; i++)
928 regmap_write(pmu_regs, ctrl->regs[i], ctrl->value);
929 }
930
931 struct samsung_retention_ctrl *
exynos_retention_init(struct samsung_pinctrl_drv_data * drvdata,const struct samsung_retention_data * data)932 exynos_retention_init(struct samsung_pinctrl_drv_data *drvdata,
933 const struct samsung_retention_data *data)
934 {
935 struct samsung_retention_ctrl *ctrl;
936 struct regmap *pmu_regs;
937 int i;
938
939 ctrl = devm_kzalloc(drvdata->dev, sizeof(*ctrl), GFP_KERNEL);
940 if (!ctrl)
941 return ERR_PTR(-ENOMEM);
942
943 pmu_regs = exynos_get_pmu_regmap();
944 if (IS_ERR(pmu_regs))
945 return ERR_CAST(pmu_regs);
946
947 ctrl->priv = pmu_regs;
948 ctrl->regs = data->regs;
949 ctrl->nr_regs = data->nr_regs;
950 ctrl->value = data->value;
951 ctrl->refcnt = data->refcnt;
952 ctrl->enable = exynos_retention_enable;
953 ctrl->disable = exynos_retention_disable;
954
955 /* Ensure that retention is disabled on driver init */
956 for (i = 0; i < ctrl->nr_regs; i++)
957 regmap_write(pmu_regs, ctrl->regs[i], ctrl->value);
958
959 return ctrl;
960 }
961