aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/pinctrl/pinctrl-exynos.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2012-12-12 15:05:15 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2012-12-12 15:05:15 -0500
commitd027db132b395dabfac208e52a7e510e441bb9d2 (patch)
tree24b055b2385f9848e77e646ce475991d8675c3c4 /drivers/pinctrl/pinctrl-exynos.c
parentd01e4afdbb65e030fd6f1f96c30a558e2eb0f279 (diff)
parent5faf7cbb848da827f6ea1458b5a1c26a44e7510a (diff)
Merge tag 'soc' of git://git.kernel.org/pub/scm/linux/kernel/git/arm/arm-soc
Pull ARM SoC updates from Olof Johansson: "This contains the bulk of new SoC development for this merge window. Two new platforms have been added, the sunxi platforms (Allwinner A1x SoCs) by Maxime Ripard, and a generic Broadcom platform for a new series of ARMv7 platforms from them, where the hope is that we can keep the platform code generic enough to have them all share one mach directory. The new Broadcom platform is contributed by Christian Daudt. Highbank has grown support for Calxeda's next generation of hardware, ECX-2000. clps711x has seen a lot of cleanup from Alexander Shiyan, and he's also taken on maintainership of the platform. Beyond this there has been a bunch of work from a number of people on converting more platforms to IRQ domains, pinctrl conversion, cleanup and general feature enablement across most of the active platforms." Fix up trivial conflicts as per Olof. * tag 'soc' of git://git.kernel.org/pub/scm/linux/kernel/git/arm/arm-soc: (174 commits) mfd: vexpress-sysreg: Remove LEDs code irqchip: irq-sunxi: Add terminating entry for sunxi_irq_dt_ids clocksource: sunxi_timer: Add terminating entry for sunxi_timer_dt_ids irq: versatile: delete dangling variable ARM: sunxi: add missing include for mdelay() ARM: EXYNOS: Avoid early use of of_machine_is_compatible() ARM: dts: add node for PL330 MDMA1 controller for exynos4 ARM: EXYNOS: Add support for secondary CPU bring-up on Exynos4412 ARM: EXYNOS: add UART3 to DEBUG_LL ports ARM: S3C24XX: Add clkdev entry for camif-upll clock ARM: SAMSUNG: Add s3c24xx/s3c64xx CAMIF GPIO setup helpers ARM: sunxi: Add missing sun4i.dtsi file pinctrl: samsung: Do not initialise statics to 0 ARM i.MX6: remove gate_mask from pllv3 ARM i.MX6: Fix ethernet PLL clocks ARM i.MX6: rename PLLs according to datasheet ARM i.MX6: Add pwm support ARM i.MX51: Add pwm support ARM i.MX53: Add pwm support ARM: mx5: Replace clk_register_clkdev with clock DT lookup ...
Diffstat (limited to 'drivers/pinctrl/pinctrl-exynos.c')
-rw-r--r--drivers/pinctrl/pinctrl-exynos.c477
1 files changed, 288 insertions, 189 deletions
diff --git a/drivers/pinctrl/pinctrl-exynos.c b/drivers/pinctrl/pinctrl-exynos.c
index 6ff665209a4c..538b9ddaadf7 100644
--- a/drivers/pinctrl/pinctrl-exynos.c
+++ b/drivers/pinctrl/pinctrl-exynos.c
@@ -41,46 +41,46 @@ static const struct of_device_id exynos_wkup_irq_ids[] = {
41 41
42static void exynos_gpio_irq_unmask(struct irq_data *irqd) 42static void exynos_gpio_irq_unmask(struct irq_data *irqd)
43{ 43{
44 struct samsung_pinctrl_drv_data *d = irqd->domain->host_data; 44 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
45 struct exynos_geint_data *edata = irq_data_get_irq_handler_data(irqd); 45 struct samsung_pinctrl_drv_data *d = bank->drvdata;
46 unsigned long reg_mask = d->ctrl->geint_mask + edata->eint_offset; 46 unsigned long reg_mask = d->ctrl->geint_mask + bank->eint_offset;
47 unsigned long mask; 47 unsigned long mask;
48 48
49 mask = readl(d->virt_base + reg_mask); 49 mask = readl(d->virt_base + reg_mask);
50 mask &= ~(1 << edata->pin); 50 mask &= ~(1 << irqd->hwirq);
51 writel(mask, d->virt_base + reg_mask); 51 writel(mask, d->virt_base + reg_mask);
52} 52}
53 53
54static void exynos_gpio_irq_mask(struct irq_data *irqd) 54static void exynos_gpio_irq_mask(struct irq_data *irqd)
55{ 55{
56 struct samsung_pinctrl_drv_data *d = irqd->domain->host_data; 56 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
57 struct exynos_geint_data *edata = irq_data_get_irq_handler_data(irqd); 57 struct samsung_pinctrl_drv_data *d = bank->drvdata;
58 unsigned long reg_mask = d->ctrl->geint_mask + edata->eint_offset; 58 unsigned long reg_mask = d->ctrl->geint_mask + bank->eint_offset;
59 unsigned long mask; 59 unsigned long mask;
60 60
61 mask = readl(d->virt_base + reg_mask); 61 mask = readl(d->virt_base + reg_mask);
62 mask |= 1 << edata->pin; 62 mask |= 1 << irqd->hwirq;
63 writel(mask, d->virt_base + reg_mask); 63 writel(mask, d->virt_base + reg_mask);
64} 64}
65 65
66static void exynos_gpio_irq_ack(struct irq_data *irqd) 66static void exynos_gpio_irq_ack(struct irq_data *irqd)
67{ 67{
68 struct samsung_pinctrl_drv_data *d = irqd->domain->host_data; 68 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
69 struct exynos_geint_data *edata = irq_data_get_irq_handler_data(irqd); 69 struct samsung_pinctrl_drv_data *d = bank->drvdata;
70 unsigned long reg_pend = d->ctrl->geint_pend + edata->eint_offset; 70 unsigned long reg_pend = d->ctrl->geint_pend + bank->eint_offset;
71 71
72 writel(1 << edata->pin, d->virt_base + reg_pend); 72 writel(1 << irqd->hwirq, d->virt_base + reg_pend);
73} 73}
74 74
75static int exynos_gpio_irq_set_type(struct irq_data *irqd, unsigned int type) 75static int exynos_gpio_irq_set_type(struct irq_data *irqd, unsigned int type)
76{ 76{
77 struct samsung_pinctrl_drv_data *d = irqd->domain->host_data; 77 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
78 struct samsung_pinctrl_drv_data *d = bank->drvdata;
78 struct samsung_pin_ctrl *ctrl = d->ctrl; 79 struct samsung_pin_ctrl *ctrl = d->ctrl;
79 struct exynos_geint_data *edata = irq_data_get_irq_handler_data(irqd); 80 unsigned int pin = irqd->hwirq;
80 struct samsung_pin_bank *bank = edata->bank; 81 unsigned int shift = EXYNOS_EINT_CON_LEN * pin;
81 unsigned int shift = EXYNOS_EINT_CON_LEN * edata->pin;
82 unsigned int con, trig_type; 82 unsigned int con, trig_type;
83 unsigned long reg_con = ctrl->geint_con + edata->eint_offset; 83 unsigned long reg_con = ctrl->geint_con + bank->eint_offset;
84 unsigned int mask; 84 unsigned int mask;
85 85
86 switch (type) { 86 switch (type) {
@@ -115,7 +115,7 @@ static int exynos_gpio_irq_set_type(struct irq_data *irqd, unsigned int type)
115 writel(con, d->virt_base + reg_con); 115 writel(con, d->virt_base + reg_con);
116 116
117 reg_con = bank->pctl_offset; 117 reg_con = bank->pctl_offset;
118 shift = edata->pin * bank->func_width; 118 shift = pin * bank->func_width;
119 mask = (1 << bank->func_width) - 1; 119 mask = (1 << bank->func_width) - 1;
120 120
121 con = readl(d->virt_base + reg_con); 121 con = readl(d->virt_base + reg_con);
@@ -137,82 +137,23 @@ static struct irq_chip exynos_gpio_irq_chip = {
137 .irq_set_type = exynos_gpio_irq_set_type, 137 .irq_set_type = exynos_gpio_irq_set_type,
138}; 138};
139 139
140/*
141 * given a controller-local external gpio interrupt number, prepare the handler
142 * data for it.
143 */
144static struct exynos_geint_data *exynos_get_eint_data(irq_hw_number_t hw,
145 struct samsung_pinctrl_drv_data *d)
146{
147 struct samsung_pin_bank *bank = d->ctrl->pin_banks;
148 struct exynos_geint_data *eint_data;
149 unsigned int nr_banks = d->ctrl->nr_banks, idx;
150 unsigned int irq_base = 0, eint_offset = 0;
151
152 if (hw >= d->ctrl->nr_gint) {
153 dev_err(d->dev, "unsupported ext-gpio interrupt\n");
154 return NULL;
155 }
156
157 for (idx = 0; idx < nr_banks; idx++, bank++) {
158 if (bank->eint_type != EINT_TYPE_GPIO)
159 continue;
160 if ((hw >= irq_base) && (hw < (irq_base + bank->nr_pins)))
161 break;
162 irq_base += bank->nr_pins;
163 eint_offset += 4;
164 }
165
166 if (idx == nr_banks) {
167 dev_err(d->dev, "pin bank not found for ext-gpio interrupt\n");
168 return NULL;
169 }
170
171 eint_data = devm_kzalloc(d->dev, sizeof(*eint_data), GFP_KERNEL);
172 if (!eint_data) {
173 dev_err(d->dev, "no memory for eint-gpio data\n");
174 return NULL;
175 }
176
177 eint_data->bank = bank;
178 eint_data->pin = hw - irq_base;
179 eint_data->eint_offset = eint_offset;
180 return eint_data;
181}
182
183static int exynos_gpio_irq_map(struct irq_domain *h, unsigned int virq, 140static int exynos_gpio_irq_map(struct irq_domain *h, unsigned int virq,
184 irq_hw_number_t hw) 141 irq_hw_number_t hw)
185{ 142{
186 struct samsung_pinctrl_drv_data *d = h->host_data; 143 struct samsung_pin_bank *b = h->host_data;
187 struct exynos_geint_data *eint_data;
188
189 eint_data = exynos_get_eint_data(hw, d);
190 if (!eint_data)
191 return -EINVAL;
192 144
193 irq_set_handler_data(virq, eint_data); 145 irq_set_chip_data(virq, b);
194 irq_set_chip_data(virq, h->host_data);
195 irq_set_chip_and_handler(virq, &exynos_gpio_irq_chip, 146 irq_set_chip_and_handler(virq, &exynos_gpio_irq_chip,
196 handle_level_irq); 147 handle_level_irq);
197 set_irq_flags(virq, IRQF_VALID); 148 set_irq_flags(virq, IRQF_VALID);
198 return 0; 149 return 0;
199} 150}
200 151
201static void exynos_gpio_irq_unmap(struct irq_domain *h, unsigned int virq)
202{
203 struct samsung_pinctrl_drv_data *d = h->host_data;
204 struct exynos_geint_data *eint_data;
205
206 eint_data = irq_get_handler_data(virq);
207 devm_kfree(d->dev, eint_data);
208}
209
210/* 152/*
211 * irq domain callbacks for external gpio interrupt controller. 153 * irq domain callbacks for external gpio interrupt controller.
212 */ 154 */
213static const struct irq_domain_ops exynos_gpio_irqd_ops = { 155static const struct irq_domain_ops exynos_gpio_irqd_ops = {
214 .map = exynos_gpio_irq_map, 156 .map = exynos_gpio_irq_map,
215 .unmap = exynos_gpio_irq_unmap,
216 .xlate = irq_domain_xlate_twocell, 157 .xlate = irq_domain_xlate_twocell,
217}; 158};
218 159
@@ -231,7 +172,7 @@ static irqreturn_t exynos_eint_gpio_irq(int irq, void *data)
231 return IRQ_HANDLED; 172 return IRQ_HANDLED;
232 bank += (group - 1); 173 bank += (group - 1);
233 174
234 virq = irq_linear_revmap(d->gpio_irqd, bank->irq_base + pin); 175 virq = irq_linear_revmap(bank->irq_domain, pin);
235 if (!virq) 176 if (!virq)
236 return IRQ_NONE; 177 return IRQ_NONE;
237 generic_handle_irq(virq); 178 generic_handle_irq(virq);
@@ -244,8 +185,10 @@ static irqreturn_t exynos_eint_gpio_irq(int irq, void *data)
244 */ 185 */
245static int exynos_eint_gpio_init(struct samsung_pinctrl_drv_data *d) 186static int exynos_eint_gpio_init(struct samsung_pinctrl_drv_data *d)
246{ 187{
188 struct samsung_pin_bank *bank;
247 struct device *dev = d->dev; 189 struct device *dev = d->dev;
248 unsigned int ret; 190 unsigned int ret;
191 unsigned int i;
249 192
250 if (!d->irq) { 193 if (!d->irq) {
251 dev_err(dev, "irq number not available\n"); 194 dev_err(dev, "irq number not available\n");
@@ -259,11 +202,16 @@ static int exynos_eint_gpio_init(struct samsung_pinctrl_drv_data *d)
259 return -ENXIO; 202 return -ENXIO;
260 } 203 }
261 204
262 d->gpio_irqd = irq_domain_add_linear(dev->of_node, d->ctrl->nr_gint, 205 bank = d->ctrl->pin_banks;
263 &exynos_gpio_irqd_ops, d); 206 for (i = 0; i < d->ctrl->nr_banks; ++i, ++bank) {
264 if (!d->gpio_irqd) { 207 if (bank->eint_type != EINT_TYPE_GPIO)
265 dev_err(dev, "gpio irq domain allocation failed\n"); 208 continue;
266 return -ENXIO; 209 bank->irq_domain = irq_domain_add_linear(bank->of_node,
210 bank->nr_pins, &exynos_gpio_irqd_ops, bank);
211 if (!bank->irq_domain) {
212 dev_err(dev, "gpio irq domain add failed\n");
213 return -ENXIO;
214 }
267 } 215 }
268 216
269 return 0; 217 return 0;
@@ -271,48 +219,46 @@ static int exynos_eint_gpio_init(struct samsung_pinctrl_drv_data *d)
271 219
272static void exynos_wkup_irq_unmask(struct irq_data *irqd) 220static void exynos_wkup_irq_unmask(struct irq_data *irqd)
273{ 221{
274 struct samsung_pinctrl_drv_data *d = irq_data_get_irq_chip_data(irqd); 222 struct samsung_pin_bank *b = irq_data_get_irq_chip_data(irqd);
275 unsigned int bank = irqd->hwirq / EXYNOS_EINT_MAX_PER_BANK; 223 struct samsung_pinctrl_drv_data *d = b->drvdata;
276 unsigned int pin = irqd->hwirq & (EXYNOS_EINT_MAX_PER_BANK - 1); 224 unsigned long reg_mask = d->ctrl->weint_mask + b->eint_offset;
277 unsigned long reg_mask = d->ctrl->weint_mask + (bank << 2);
278 unsigned long mask; 225 unsigned long mask;
279 226
280 mask = readl(d->virt_base + reg_mask); 227 mask = readl(d->virt_base + reg_mask);
281 mask &= ~(1 << pin); 228 mask &= ~(1 << irqd->hwirq);
282 writel(mask, d->virt_base + reg_mask); 229 writel(mask, d->virt_base + reg_mask);
283} 230}
284 231
285static void exynos_wkup_irq_mask(struct irq_data *irqd) 232static void exynos_wkup_irq_mask(struct irq_data *irqd)
286{ 233{
287 struct samsung_pinctrl_drv_data *d = irq_data_get_irq_chip_data(irqd); 234 struct samsung_pin_bank *b = irq_data_get_irq_chip_data(irqd);
288 unsigned int bank = irqd->hwirq / EXYNOS_EINT_MAX_PER_BANK; 235 struct samsung_pinctrl_drv_data *d = b->drvdata;
289 unsigned int pin = irqd->hwirq & (EXYNOS_EINT_MAX_PER_BANK - 1); 236 unsigned long reg_mask = d->ctrl->weint_mask + b->eint_offset;
290 unsigned long reg_mask = d->ctrl->weint_mask + (bank << 2);
291 unsigned long mask; 237 unsigned long mask;
292 238
293 mask = readl(d->virt_base + reg_mask); 239 mask = readl(d->virt_base + reg_mask);
294 mask |= 1 << pin; 240 mask |= 1 << irqd->hwirq;
295 writel(mask, d->virt_base + reg_mask); 241 writel(mask, d->virt_base + reg_mask);
296} 242}
297 243
298static void exynos_wkup_irq_ack(struct irq_data *irqd) 244static void exynos_wkup_irq_ack(struct irq_data *irqd)
299{ 245{
300 struct samsung_pinctrl_drv_data *d = irq_data_get_irq_chip_data(irqd); 246 struct samsung_pin_bank *b = irq_data_get_irq_chip_data(irqd);
301 unsigned int bank = irqd->hwirq / EXYNOS_EINT_MAX_PER_BANK; 247 struct samsung_pinctrl_drv_data *d = b->drvdata;
302 unsigned int pin = irqd->hwirq & (EXYNOS_EINT_MAX_PER_BANK - 1); 248 unsigned long pend = d->ctrl->weint_pend + b->eint_offset;
303 unsigned long pend = d->ctrl->weint_pend + (bank << 2);
304 249
305 writel(1 << pin, d->virt_base + pend); 250 writel(1 << irqd->hwirq, d->virt_base + pend);
306} 251}
307 252
308static int exynos_wkup_irq_set_type(struct irq_data *irqd, unsigned int type) 253static int exynos_wkup_irq_set_type(struct irq_data *irqd, unsigned int type)
309{ 254{
310 struct samsung_pinctrl_drv_data *d = irq_data_get_irq_chip_data(irqd); 255 struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd);
311 unsigned int bank = irqd->hwirq / EXYNOS_EINT_MAX_PER_BANK; 256 struct samsung_pinctrl_drv_data *d = bank->drvdata;
312 unsigned int pin = irqd->hwirq & (EXYNOS_EINT_MAX_PER_BANK - 1); 257 unsigned int pin = irqd->hwirq;
313 unsigned long reg_con = d->ctrl->weint_con + (bank << 2); 258 unsigned long reg_con = d->ctrl->weint_con + bank->eint_offset;
314 unsigned long shift = EXYNOS_EINT_CON_LEN * pin; 259 unsigned long shift = EXYNOS_EINT_CON_LEN * pin;
315 unsigned long con, trig_type; 260 unsigned long con, trig_type;
261 unsigned int mask;
316 262
317 switch (type) { 263 switch (type) {
318 case IRQ_TYPE_EDGE_RISING: 264 case IRQ_TYPE_EDGE_RISING:
@@ -344,6 +290,16 @@ static int exynos_wkup_irq_set_type(struct irq_data *irqd, unsigned int type)
344 con &= ~(EXYNOS_EINT_CON_MASK << shift); 290 con &= ~(EXYNOS_EINT_CON_MASK << shift);
345 con |= trig_type << shift; 291 con |= trig_type << shift;
346 writel(con, d->virt_base + reg_con); 292 writel(con, d->virt_base + reg_con);
293
294 reg_con = bank->pctl_offset;
295 shift = pin * bank->func_width;
296 mask = (1 << bank->func_width) - 1;
297
298 con = readl(d->virt_base + reg_con);
299 con &= ~(mask << shift);
300 con |= EXYNOS_EINT_FUNC << shift;
301 writel(con, d->virt_base + reg_con);
302
347 return 0; 303 return 0;
348} 304}
349 305
@@ -362,6 +318,7 @@ static struct irq_chip exynos_wkup_irq_chip = {
362static void exynos_irq_eint0_15(unsigned int irq, struct irq_desc *desc) 318static void exynos_irq_eint0_15(unsigned int irq, struct irq_desc *desc)
363{ 319{
364 struct exynos_weint_data *eintd = irq_get_handler_data(irq); 320 struct exynos_weint_data *eintd = irq_get_handler_data(irq);
321 struct samsung_pin_bank *bank = eintd->bank;
365 struct irq_chip *chip = irq_get_chip(irq); 322 struct irq_chip *chip = irq_get_chip(irq);
366 int eint_irq; 323 int eint_irq;
367 324
@@ -371,20 +328,20 @@ static void exynos_irq_eint0_15(unsigned int irq, struct irq_desc *desc)
371 if (chip->irq_ack) 328 if (chip->irq_ack)
372 chip->irq_ack(&desc->irq_data); 329 chip->irq_ack(&desc->irq_data);
373 330
374 eint_irq = irq_linear_revmap(eintd->domain, eintd->irq); 331 eint_irq = irq_linear_revmap(bank->irq_domain, eintd->irq);
375 generic_handle_irq(eint_irq); 332 generic_handle_irq(eint_irq);
376 chip->irq_unmask(&desc->irq_data); 333 chip->irq_unmask(&desc->irq_data);
377 chained_irq_exit(chip, desc); 334 chained_irq_exit(chip, desc);
378} 335}
379 336
380static inline void exynos_irq_demux_eint(int irq_base, unsigned long pend, 337static inline void exynos_irq_demux_eint(unsigned long pend,
381 struct irq_domain *domain) 338 struct irq_domain *domain)
382{ 339{
383 unsigned int irq; 340 unsigned int irq;
384 341
385 while (pend) { 342 while (pend) {
386 irq = fls(pend) - 1; 343 irq = fls(pend) - 1;
387 generic_handle_irq(irq_find_mapping(domain, irq_base + irq)); 344 generic_handle_irq(irq_find_mapping(domain, irq));
388 pend &= ~(1 << irq); 345 pend &= ~(1 << irq);
389 } 346 }
390} 347}
@@ -393,18 +350,22 @@ static inline void exynos_irq_demux_eint(int irq_base, unsigned long pend,
393static void exynos_irq_demux_eint16_31(unsigned int irq, struct irq_desc *desc) 350static void exynos_irq_demux_eint16_31(unsigned int irq, struct irq_desc *desc)
394{ 351{
395 struct irq_chip *chip = irq_get_chip(irq); 352 struct irq_chip *chip = irq_get_chip(irq);
396 struct exynos_weint_data *eintd = irq_get_handler_data(irq); 353 struct exynos_muxed_weint_data *eintd = irq_get_handler_data(irq);
397 struct samsung_pinctrl_drv_data *d = eintd->domain->host_data; 354 struct samsung_pinctrl_drv_data *d = eintd->banks[0]->drvdata;
355 struct samsung_pin_ctrl *ctrl = d->ctrl;
398 unsigned long pend; 356 unsigned long pend;
399 unsigned long mask; 357 unsigned long mask;
358 int i;
400 359
401 chained_irq_enter(chip, desc); 360 chained_irq_enter(chip, desc);
402 pend = readl(d->virt_base + d->ctrl->weint_pend + 0x8); 361
403 mask = readl(d->virt_base + d->ctrl->weint_mask + 0x8); 362 for (i = 0; i < eintd->nr_banks; ++i) {
404 exynos_irq_demux_eint(16, pend & ~mask, eintd->domain); 363 struct samsung_pin_bank *b = eintd->banks[i];
405 pend = readl(d->virt_base + d->ctrl->weint_pend + 0xC); 364 pend = readl(d->virt_base + ctrl->weint_pend + b->eint_offset);
406 mask = readl(d->virt_base + d->ctrl->weint_mask + 0xC); 365 mask = readl(d->virt_base + ctrl->weint_mask + b->eint_offset);
407 exynos_irq_demux_eint(24, pend & ~mask, eintd->domain); 366 exynos_irq_demux_eint(pend & ~mask, b->irq_domain);
367 }
368
408 chained_irq_exit(chip, desc); 369 chained_irq_exit(chip, desc);
409} 370}
410 371
@@ -434,7 +395,11 @@ static int exynos_eint_wkup_init(struct samsung_pinctrl_drv_data *d)
434 struct device *dev = d->dev; 395 struct device *dev = d->dev;
435 struct device_node *wkup_np = NULL; 396 struct device_node *wkup_np = NULL;
436 struct device_node *np; 397 struct device_node *np;
398 struct samsung_pin_bank *bank;
437 struct exynos_weint_data *weint_data; 399 struct exynos_weint_data *weint_data;
400 struct exynos_muxed_weint_data *muxed_data;
401 unsigned int muxed_banks = 0;
402 unsigned int i;
438 int idx, irq; 403 int idx, irq;
439 404
440 for_each_child_of_node(dev->of_node, np) { 405 for_each_child_of_node(dev->of_node, np) {
@@ -446,90 +411,124 @@ static int exynos_eint_wkup_init(struct samsung_pinctrl_drv_data *d)
446 if (!wkup_np) 411 if (!wkup_np)
447 return -ENODEV; 412 return -ENODEV;
448 413
449 d->wkup_irqd = irq_domain_add_linear(wkup_np, d->ctrl->nr_wint, 414 bank = d->ctrl->pin_banks;
450 &exynos_wkup_irqd_ops, d); 415 for (i = 0; i < d->ctrl->nr_banks; ++i, ++bank) {
451 if (!d->wkup_irqd) { 416 if (bank->eint_type != EINT_TYPE_WKUP)
452 dev_err(dev, "wakeup irq domain allocation failed\n"); 417 continue;
453 return -ENXIO;
454 }
455 418
456 weint_data = devm_kzalloc(dev, sizeof(*weint_data) * 17, GFP_KERNEL); 419 bank->irq_domain = irq_domain_add_linear(bank->of_node,
457 if (!weint_data) { 420 bank->nr_pins, &exynos_wkup_irqd_ops, bank);
458 dev_err(dev, "could not allocate memory for weint_data\n"); 421 if (!bank->irq_domain) {
459 return -ENOMEM; 422 dev_err(dev, "wkup irq domain add failed\n");
460 } 423 return -ENXIO;
424 }
461 425
462 irq = irq_of_parse_and_map(wkup_np, 16); 426 if (!of_find_property(bank->of_node, "interrupts", NULL)) {
463 if (irq) { 427 bank->eint_type = EINT_TYPE_WKUP_MUX;
464 weint_data[16].domain = d->wkup_irqd; 428 ++muxed_banks;
465 irq_set_chained_handler(irq, exynos_irq_demux_eint16_31); 429 continue;
466 irq_set_handler_data(irq, &weint_data[16]); 430 }
467 } else {
468 dev_err(dev, "irq number for EINT16-32 not found\n");
469 }
470 431
471 for (idx = 0; idx < 16; idx++) { 432 weint_data = devm_kzalloc(dev, bank->nr_pins
472 weint_data[idx].domain = d->wkup_irqd; 433 * sizeof(*weint_data), GFP_KERNEL);
473 weint_data[idx].irq = idx; 434 if (!weint_data) {
435 dev_err(dev, "could not allocate memory for weint_data\n");
436 return -ENOMEM;
437 }
474 438
475 irq = irq_of_parse_and_map(wkup_np, idx); 439 for (idx = 0; idx < bank->nr_pins; ++idx) {
476 if (irq) { 440 irq = irq_of_parse_and_map(bank->of_node, idx);
441 if (!irq) {
442 dev_err(dev, "irq number for eint-%s-%d not found\n",
443 bank->name, idx);
444 continue;
445 }
446 weint_data[idx].irq = idx;
447 weint_data[idx].bank = bank;
477 irq_set_handler_data(irq, &weint_data[idx]); 448 irq_set_handler_data(irq, &weint_data[idx]);
478 irq_set_chained_handler(irq, exynos_irq_eint0_15); 449 irq_set_chained_handler(irq, exynos_irq_eint0_15);
479 } else {
480 dev_err(dev, "irq number for eint-%x not found\n", idx);
481 } 450 }
482 } 451 }
452
453 if (!muxed_banks)
454 return 0;
455
456 irq = irq_of_parse_and_map(wkup_np, 0);
457 if (!irq) {
458 dev_err(dev, "irq number for muxed EINTs not found\n");
459 return 0;
460 }
461
462 muxed_data = devm_kzalloc(dev, sizeof(*muxed_data)
463 + muxed_banks*sizeof(struct samsung_pin_bank *), GFP_KERNEL);
464 if (!muxed_data) {
465 dev_err(dev, "could not allocate memory for muxed_data\n");
466 return -ENOMEM;
467 }
468
469 irq_set_chained_handler(irq, exynos_irq_demux_eint16_31);
470 irq_set_handler_data(irq, muxed_data);
471
472 bank = d->ctrl->pin_banks;
473 idx = 0;
474 for (i = 0; i < d->ctrl->nr_banks; ++i, ++bank) {
475 if (bank->eint_type != EINT_TYPE_WKUP_MUX)
476 continue;
477
478 muxed_data->banks[idx++] = bank;
479 }
480 muxed_data->nr_banks = muxed_banks;
481
483 return 0; 482 return 0;
484} 483}
485 484
486/* pin banks of exynos4210 pin-controller 0 */ 485/* pin banks of exynos4210 pin-controller 0 */
487static struct samsung_pin_bank exynos4210_pin_banks0[] = { 486static struct samsung_pin_bank exynos4210_pin_banks0[] = {
488 EXYNOS_PIN_BANK_EINTG(0x000, EXYNOS4210_GPIO_A0, "gpa0"), 487 EXYNOS_PIN_BANK_EINTG(8, 0x000, "gpa0", 0x00),
489 EXYNOS_PIN_BANK_EINTG(0x020, EXYNOS4210_GPIO_A1, "gpa1"), 488 EXYNOS_PIN_BANK_EINTG(6, 0x020, "gpa1", 0x04),
490 EXYNOS_PIN_BANK_EINTG(0x040, EXYNOS4210_GPIO_B, "gpb"), 489 EXYNOS_PIN_BANK_EINTG(8, 0x040, "gpb", 0x08),
491 EXYNOS_PIN_BANK_EINTG(0x060, EXYNOS4210_GPIO_C0, "gpc0"), 490 EXYNOS_PIN_BANK_EINTG(5, 0x060, "gpc0", 0x0c),
492 EXYNOS_PIN_BANK_EINTG(0x080, EXYNOS4210_GPIO_C1, "gpc1"), 491 EXYNOS_PIN_BANK_EINTG(5, 0x080, "gpc1", 0x10),
493 EXYNOS_PIN_BANK_EINTG(0x0A0, EXYNOS4210_GPIO_D0, "gpd0"), 492 EXYNOS_PIN_BANK_EINTG(4, 0x0A0, "gpd0", 0x14),
494 EXYNOS_PIN_BANK_EINTG(0x0C0, EXYNOS4210_GPIO_D1, "gpd1"), 493 EXYNOS_PIN_BANK_EINTG(4, 0x0C0, "gpd1", 0x18),
495 EXYNOS_PIN_BANK_EINTG(0x0E0, EXYNOS4210_GPIO_E0, "gpe0"), 494 EXYNOS_PIN_BANK_EINTG(5, 0x0E0, "gpe0", 0x1c),
496 EXYNOS_PIN_BANK_EINTG(0x100, EXYNOS4210_GPIO_E1, "gpe1"), 495 EXYNOS_PIN_BANK_EINTG(8, 0x100, "gpe1", 0x20),
497 EXYNOS_PIN_BANK_EINTG(0x120, EXYNOS4210_GPIO_E2, "gpe2"), 496 EXYNOS_PIN_BANK_EINTG(6, 0x120, "gpe2", 0x24),
498 EXYNOS_PIN_BANK_EINTG(0x140, EXYNOS4210_GPIO_E3, "gpe3"), 497 EXYNOS_PIN_BANK_EINTG(8, 0x140, "gpe3", 0x28),
499 EXYNOS_PIN_BANK_EINTG(0x160, EXYNOS4210_GPIO_E4, "gpe4"), 498 EXYNOS_PIN_BANK_EINTG(8, 0x160, "gpe4", 0x2c),
500 EXYNOS_PIN_BANK_EINTG(0x180, EXYNOS4210_GPIO_F0, "gpf0"), 499 EXYNOS_PIN_BANK_EINTG(8, 0x180, "gpf0", 0x30),
501 EXYNOS_PIN_BANK_EINTG(0x1A0, EXYNOS4210_GPIO_F1, "gpf1"), 500 EXYNOS_PIN_BANK_EINTG(8, 0x1A0, "gpf1", 0x34),
502 EXYNOS_PIN_BANK_EINTG(0x1C0, EXYNOS4210_GPIO_F2, "gpf2"), 501 EXYNOS_PIN_BANK_EINTG(8, 0x1C0, "gpf2", 0x38),
503 EXYNOS_PIN_BANK_EINTG(0x1E0, EXYNOS4210_GPIO_F3, "gpf3"), 502 EXYNOS_PIN_BANK_EINTG(6, 0x1E0, "gpf3", 0x3c),
504}; 503};
505 504
506/* pin banks of exynos4210 pin-controller 1 */ 505/* pin banks of exynos4210 pin-controller 1 */
507static struct samsung_pin_bank exynos4210_pin_banks1[] = { 506static struct samsung_pin_bank exynos4210_pin_banks1[] = {
508 EXYNOS_PIN_BANK_EINTG(0x000, EXYNOS4210_GPIO_J0, "gpj0"), 507 EXYNOS_PIN_BANK_EINTG(8, 0x000, "gpj0", 0x00),
509 EXYNOS_PIN_BANK_EINTG(0x020, EXYNOS4210_GPIO_J1, "gpj1"), 508 EXYNOS_PIN_BANK_EINTG(5, 0x020, "gpj1", 0x04),
510 EXYNOS_PIN_BANK_EINTG(0x040, EXYNOS4210_GPIO_K0, "gpk0"), 509 EXYNOS_PIN_BANK_EINTG(7, 0x040, "gpk0", 0x08),
511 EXYNOS_PIN_BANK_EINTG(0x060, EXYNOS4210_GPIO_K1, "gpk1"), 510 EXYNOS_PIN_BANK_EINTG(7, 0x060, "gpk1", 0x0c),
512 EXYNOS_PIN_BANK_EINTG(0x080, EXYNOS4210_GPIO_K2, "gpk2"), 511 EXYNOS_PIN_BANK_EINTG(7, 0x080, "gpk2", 0x10),
513 EXYNOS_PIN_BANK_EINTG(0x0A0, EXYNOS4210_GPIO_K3, "gpk3"), 512 EXYNOS_PIN_BANK_EINTG(7, 0x0A0, "gpk3", 0x14),
514 EXYNOS_PIN_BANK_EINTG(0x0C0, EXYNOS4210_GPIO_L0, "gpl0"), 513 EXYNOS_PIN_BANK_EINTG(8, 0x0C0, "gpl0", 0x18),
515 EXYNOS_PIN_BANK_EINTG(0x0E0, EXYNOS4210_GPIO_L1, "gpl1"), 514 EXYNOS_PIN_BANK_EINTG(3, 0x0E0, "gpl1", 0x1c),
516 EXYNOS_PIN_BANK_EINTG(0x100, EXYNOS4210_GPIO_L2, "gpl2"), 515 EXYNOS_PIN_BANK_EINTG(8, 0x100, "gpl2", 0x20),
517 EXYNOS_PIN_BANK_EINTN(0x120, EXYNOS4210_GPIO_Y0, "gpy0"), 516 EXYNOS_PIN_BANK_EINTN(6, 0x120, "gpy0"),
518 EXYNOS_PIN_BANK_EINTN(0x140, EXYNOS4210_GPIO_Y1, "gpy1"), 517 EXYNOS_PIN_BANK_EINTN(4, 0x140, "gpy1"),
519 EXYNOS_PIN_BANK_EINTN(0x160, EXYNOS4210_GPIO_Y2, "gpy2"), 518 EXYNOS_PIN_BANK_EINTN(6, 0x160, "gpy2"),
520 EXYNOS_PIN_BANK_EINTN(0x180, EXYNOS4210_GPIO_Y3, "gpy3"), 519 EXYNOS_PIN_BANK_EINTN(8, 0x180, "gpy3"),
521 EXYNOS_PIN_BANK_EINTN(0x1A0, EXYNOS4210_GPIO_Y4, "gpy4"), 520 EXYNOS_PIN_BANK_EINTN(8, 0x1A0, "gpy4"),
522 EXYNOS_PIN_BANK_EINTN(0x1C0, EXYNOS4210_GPIO_Y5, "gpy5"), 521 EXYNOS_PIN_BANK_EINTN(8, 0x1C0, "gpy5"),
523 EXYNOS_PIN_BANK_EINTN(0x1E0, EXYNOS4210_GPIO_Y6, "gpy6"), 522 EXYNOS_PIN_BANK_EINTN(8, 0x1E0, "gpy6"),
524 EXYNOS_PIN_BANK_EINTN(0xC00, EXYNOS4210_GPIO_X0, "gpx0"), 523 EXYNOS_PIN_BANK_EINTW(8, 0xC00, "gpx0", 0x00),
525 EXYNOS_PIN_BANK_EINTN(0xC20, EXYNOS4210_GPIO_X1, "gpx1"), 524 EXYNOS_PIN_BANK_EINTW(8, 0xC20, "gpx1", 0x04),
526 EXYNOS_PIN_BANK_EINTN(0xC40, EXYNOS4210_GPIO_X2, "gpx2"), 525 EXYNOS_PIN_BANK_EINTW(8, 0xC40, "gpx2", 0x08),
527 EXYNOS_PIN_BANK_EINTN(0xC60, EXYNOS4210_GPIO_X3, "gpx3"), 526 EXYNOS_PIN_BANK_EINTW(8, 0xC60, "gpx3", 0x0c),
528}; 527};
529 528
530/* pin banks of exynos4210 pin-controller 2 */ 529/* pin banks of exynos4210 pin-controller 2 */
531static struct samsung_pin_bank exynos4210_pin_banks2[] = { 530static struct samsung_pin_bank exynos4210_pin_banks2[] = {
532 EXYNOS_PIN_BANK_EINTN(0x000, EXYNOS4210_GPIO_Z, "gpz"), 531 EXYNOS_PIN_BANK_EINTN(7, 0x000, "gpz"),
533}; 532};
534 533
535/* 534/*
@@ -541,9 +540,6 @@ struct samsung_pin_ctrl exynos4210_pin_ctrl[] = {
541 /* pin-controller instance 0 data */ 540 /* pin-controller instance 0 data */
542 .pin_banks = exynos4210_pin_banks0, 541 .pin_banks = exynos4210_pin_banks0,
543 .nr_banks = ARRAY_SIZE(exynos4210_pin_banks0), 542 .nr_banks = ARRAY_SIZE(exynos4210_pin_banks0),
544 .base = EXYNOS4210_GPIO_A0_START,
545 .nr_pins = EXYNOS4210_GPIOA_NR_PINS,
546 .nr_gint = EXYNOS4210_GPIOA_NR_GINT,
547 .geint_con = EXYNOS_GPIO_ECON_OFFSET, 543 .geint_con = EXYNOS_GPIO_ECON_OFFSET,
548 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET, 544 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET,
549 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET, 545 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET,
@@ -554,10 +550,6 @@ struct samsung_pin_ctrl exynos4210_pin_ctrl[] = {
554 /* pin-controller instance 1 data */ 550 /* pin-controller instance 1 data */
555 .pin_banks = exynos4210_pin_banks1, 551 .pin_banks = exynos4210_pin_banks1,
556 .nr_banks = ARRAY_SIZE(exynos4210_pin_banks1), 552 .nr_banks = ARRAY_SIZE(exynos4210_pin_banks1),
557 .base = EXYNOS4210_GPIOA_NR_PINS,
558 .nr_pins = EXYNOS4210_GPIOB_NR_PINS,
559 .nr_gint = EXYNOS4210_GPIOB_NR_GINT,
560 .nr_wint = 32,
561 .geint_con = EXYNOS_GPIO_ECON_OFFSET, 553 .geint_con = EXYNOS_GPIO_ECON_OFFSET,
562 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET, 554 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET,
563 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET, 555 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET,
@@ -572,9 +564,116 @@ struct samsung_pin_ctrl exynos4210_pin_ctrl[] = {
572 /* pin-controller instance 2 data */ 564 /* pin-controller instance 2 data */
573 .pin_banks = exynos4210_pin_banks2, 565 .pin_banks = exynos4210_pin_banks2,
574 .nr_banks = ARRAY_SIZE(exynos4210_pin_banks2), 566 .nr_banks = ARRAY_SIZE(exynos4210_pin_banks2),
575 .base = EXYNOS4210_GPIOA_NR_PINS +
576 EXYNOS4210_GPIOB_NR_PINS,
577 .nr_pins = EXYNOS4210_GPIOC_NR_PINS,
578 .label = "exynos4210-gpio-ctrl2", 567 .label = "exynos4210-gpio-ctrl2",
579 }, 568 },
580}; 569};
570
571/* pin banks of exynos4x12 pin-controller 0 */
572static struct samsung_pin_bank exynos4x12_pin_banks0[] = {
573 EXYNOS_PIN_BANK_EINTG(8, 0x000, "gpa0", 0x00),
574 EXYNOS_PIN_BANK_EINTG(6, 0x020, "gpa1", 0x04),
575 EXYNOS_PIN_BANK_EINTG(8, 0x040, "gpb", 0x08),
576 EXYNOS_PIN_BANK_EINTG(5, 0x060, "gpc0", 0x0c),
577 EXYNOS_PIN_BANK_EINTG(5, 0x080, "gpc1", 0x10),
578 EXYNOS_PIN_BANK_EINTG(4, 0x0A0, "gpd0", 0x14),
579 EXYNOS_PIN_BANK_EINTG(4, 0x0C0, "gpd1", 0x18),
580 EXYNOS_PIN_BANK_EINTG(8, 0x180, "gpf0", 0x30),
581 EXYNOS_PIN_BANK_EINTG(8, 0x1A0, "gpf1", 0x34),
582 EXYNOS_PIN_BANK_EINTG(8, 0x1C0, "gpf2", 0x38),
583 EXYNOS_PIN_BANK_EINTG(6, 0x1E0, "gpf3", 0x3c),
584 EXYNOS_PIN_BANK_EINTG(8, 0x240, "gpj0", 0x40),
585 EXYNOS_PIN_BANK_EINTG(5, 0x260, "gpj1", 0x44),
586};
587
588/* pin banks of exynos4x12 pin-controller 1 */
589static struct samsung_pin_bank exynos4x12_pin_banks1[] = {
590 EXYNOS_PIN_BANK_EINTG(7, 0x040, "gpk0", 0x08),
591 EXYNOS_PIN_BANK_EINTG(7, 0x060, "gpk1", 0x0c),
592 EXYNOS_PIN_BANK_EINTG(7, 0x080, "gpk2", 0x10),
593 EXYNOS_PIN_BANK_EINTG(7, 0x0A0, "gpk3", 0x14),
594 EXYNOS_PIN_BANK_EINTG(7, 0x0C0, "gpl0", 0x18),
595 EXYNOS_PIN_BANK_EINTG(2, 0x0E0, "gpl1", 0x1c),
596 EXYNOS_PIN_BANK_EINTG(8, 0x100, "gpl2", 0x20),
597 EXYNOS_PIN_BANK_EINTG(8, 0x260, "gpm0", 0x24),
598 EXYNOS_PIN_BANK_EINTG(7, 0x280, "gpm1", 0x28),
599 EXYNOS_PIN_BANK_EINTG(5, 0x2A0, "gpm2", 0x2c),
600 EXYNOS_PIN_BANK_EINTG(8, 0x2C0, "gpm3", 0x30),
601 EXYNOS_PIN_BANK_EINTG(8, 0x2E0, "gpm4", 0x34),
602 EXYNOS_PIN_BANK_EINTN(6, 0x120, "gpy0"),
603 EXYNOS_PIN_BANK_EINTN(4, 0x140, "gpy1"),
604 EXYNOS_PIN_BANK_EINTN(6, 0x160, "gpy2"),
605 EXYNOS_PIN_BANK_EINTN(8, 0x180, "gpy3"),
606 EXYNOS_PIN_BANK_EINTN(8, 0x1A0, "gpy4"),
607 EXYNOS_PIN_BANK_EINTN(8, 0x1C0, "gpy5"),
608 EXYNOS_PIN_BANK_EINTN(8, 0x1E0, "gpy6"),
609 EXYNOS_PIN_BANK_EINTW(8, 0xC00, "gpx0", 0x00),
610 EXYNOS_PIN_BANK_EINTW(8, 0xC20, "gpx1", 0x04),
611 EXYNOS_PIN_BANK_EINTW(8, 0xC40, "gpx2", 0x08),
612 EXYNOS_PIN_BANK_EINTW(8, 0xC60, "gpx3", 0x0c),
613};
614
615/* pin banks of exynos4x12 pin-controller 2 */
616static struct samsung_pin_bank exynos4x12_pin_banks2[] = {
617 EXYNOS_PIN_BANK_EINTG(7, 0x000, "gpz", 0x00),
618};
619
620/* pin banks of exynos4x12 pin-controller 3 */
621static struct samsung_pin_bank exynos4x12_pin_banks3[] = {
622 EXYNOS_PIN_BANK_EINTG(8, 0x000, "gpv0", 0x00),
623 EXYNOS_PIN_BANK_EINTG(8, 0x020, "gpv1", 0x04),
624 EXYNOS_PIN_BANK_EINTG(8, 0x040, "gpv2", 0x08),
625 EXYNOS_PIN_BANK_EINTG(8, 0x060, "gpv3", 0x0c),
626 EXYNOS_PIN_BANK_EINTG(2, 0x080, "gpv4", 0x10),
627};
628
629/*
630 * Samsung pinctrl driver data for Exynos4x12 SoC. Exynos4x12 SoC includes
631 * four gpio/pin-mux/pinconfig controllers.
632 */
633struct samsung_pin_ctrl exynos4x12_pin_ctrl[] = {
634 {
635 /* pin-controller instance 0 data */
636 .pin_banks = exynos4x12_pin_banks0,
637 .nr_banks = ARRAY_SIZE(exynos4x12_pin_banks0),
638 .geint_con = EXYNOS_GPIO_ECON_OFFSET,
639 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET,
640 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET,
641 .svc = EXYNOS_SVC_OFFSET,
642 .eint_gpio_init = exynos_eint_gpio_init,
643 .label = "exynos4x12-gpio-ctrl0",
644 }, {
645 /* pin-controller instance 1 data */
646 .pin_banks = exynos4x12_pin_banks1,
647 .nr_banks = ARRAY_SIZE(exynos4x12_pin_banks1),
648 .geint_con = EXYNOS_GPIO_ECON_OFFSET,
649 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET,
650 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET,
651 .weint_con = EXYNOS_WKUP_ECON_OFFSET,
652 .weint_mask = EXYNOS_WKUP_EMASK_OFFSET,
653 .weint_pend = EXYNOS_WKUP_EPEND_OFFSET,
654 .svc = EXYNOS_SVC_OFFSET,
655 .eint_gpio_init = exynos_eint_gpio_init,
656 .eint_wkup_init = exynos_eint_wkup_init,
657 .label = "exynos4x12-gpio-ctrl1",
658 }, {
659 /* pin-controller instance 2 data */
660 .pin_banks = exynos4x12_pin_banks2,
661 .nr_banks = ARRAY_SIZE(exynos4x12_pin_banks2),
662 .geint_con = EXYNOS_GPIO_ECON_OFFSET,
663 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET,
664 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET,
665 .svc = EXYNOS_SVC_OFFSET,
666 .eint_gpio_init = exynos_eint_gpio_init,
667 .label = "exynos4x12-gpio-ctrl2",
668 }, {
669 /* pin-controller instance 3 data */
670 .pin_banks = exynos4x12_pin_banks3,
671 .nr_banks = ARRAY_SIZE(exynos4x12_pin_banks3),
672 .geint_con = EXYNOS_GPIO_ECON_OFFSET,
673 .geint_mask = EXYNOS_GPIO_EMASK_OFFSET,
674 .geint_pend = EXYNOS_GPIO_EPEND_OFFSET,
675 .svc = EXYNOS_SVC_OFFSET,
676 .eint_gpio_init = exynos_eint_gpio_init,
677 .label = "exynos4x12-gpio-ctrl3",
678 },
679};