1/* 2 * Copyright (c) 2009-2011 Samsung Electronics Co., Ltd. 3 * http://www.samsung.com/ 4 * 5 * Copyright 2008 Openmoko, Inc. 6 * Copyright 2008 Simtec Electronics 7 * Ben Dooks <ben@simtec.co.uk> 8 * http://armlinux.simtec.co.uk/ 9 * 10 * SAMSUNG - GPIOlib support 11 * 12 * This program is free software; you can redistribute it and/or modify 13 * it under the terms of the GNU General Public License version 2 as 14 * published by the Free Software Foundation. 15 */ 16 17#include <linux/kernel.h> 18#include <linux/irq.h> 19#include <linux/io.h> 20#include <linux/gpio.h> 21#include <linux/init.h> 22#include <linux/spinlock.h> 23#include <linux/module.h> 24#include <linux/interrupt.h> 25#include <linux/device.h> 26#include <linux/ioport.h> 27#include <linux/of.h> 28#include <linux/slab.h> 29#include <linux/of_address.h> 30 31#include <asm/irq.h> 32 33#include <mach/hardware.h> 34#include <mach/map.h> 35#include <mach/regs-clock.h> 36#include <mach/regs-gpio.h> 37 38#include <plat/cpu.h> 39#include <plat/gpio-core.h> 40#include <plat/gpio-cfg.h> 41#include <plat/gpio-cfg-helpers.h> 42#include <plat/gpio-fns.h> 43#include <plat/pm.h> 44 45#ifndef DEBUG_GPIO 46#define gpio_dbg(x...) do { } while (0) 47#else 48#define gpio_dbg(x...) printk(KERN_DEBUG x) 49#endif 50 51int samsung_gpio_setpull_updown(struct samsung_gpio_chip *chip, 52 unsigned int off, samsung_gpio_pull_t pull) 53{ 54 void __iomem *reg = chip->base + 0x08; 55 int shift = off * 2; 56 u32 pup; 57 58 pup = __raw_readl(reg); 59 pup &= ~(3 << shift); 60 pup |= pull << shift; 61 __raw_writel(pup, reg); 62 63 return 0; 64} 65 66samsung_gpio_pull_t samsung_gpio_getpull_updown(struct samsung_gpio_chip *chip, 67 unsigned int off) 68{ 69 void __iomem *reg = chip->base + 0x08; 70 int shift = off * 2; 71 u32 pup = __raw_readl(reg); 72 73 pup >>= shift; 74 pup &= 0x3; 75 76 return (__force samsung_gpio_pull_t)pup; 77} 78 79int s3c2443_gpio_setpull(struct samsung_gpio_chip *chip, 80 unsigned int off, samsung_gpio_pull_t pull) 81{ 82 switch (pull) { 83 case S3C_GPIO_PULL_NONE: 84 pull = 0x01; 85 break; 86 case S3C_GPIO_PULL_UP: 87 pull = 0x00; 88 break; 89 case S3C_GPIO_PULL_DOWN: 90 pull = 0x02; 91 break; 92 } 93 return samsung_gpio_setpull_updown(chip, off, pull); 94} 95 96samsung_gpio_pull_t s3c2443_gpio_getpull(struct samsung_gpio_chip *chip, 97 unsigned int off) 98{ 99 samsung_gpio_pull_t pull; 100 101 pull = samsung_gpio_getpull_updown(chip, off); 102 103 switch (pull) { 104 case 0x00: 105 pull = S3C_GPIO_PULL_UP; 106 break; 107 case 0x01: 108 case 0x03: 109 pull = S3C_GPIO_PULL_NONE; 110 break; 111 case 0x02: 112 pull = S3C_GPIO_PULL_DOWN; 113 break; 114 } 115 116 return pull; 117} 118 119static int s3c24xx_gpio_setpull_1(struct samsung_gpio_chip *chip, 120 unsigned int off, samsung_gpio_pull_t pull, 121 samsung_gpio_pull_t updown) 122{ 123 void __iomem *reg = chip->base + 0x08; 124 u32 pup = __raw_readl(reg); 125 126 if (pull == updown) 127 pup &= ~(1 << off); 128 else if (pull == S3C_GPIO_PULL_NONE) 129 pup |= (1 << off); 130 else 131 return -EINVAL; 132 133 __raw_writel(pup, reg); 134 return 0; 135} 136 137static samsung_gpio_pull_t s3c24xx_gpio_getpull_1(struct samsung_gpio_chip *chip, 138 unsigned int off, 139 samsung_gpio_pull_t updown) 140{ 141 void __iomem *reg = chip->base + 0x08; 142 u32 pup = __raw_readl(reg); 143 144 pup &= (1 << off); 145 return pup ? S3C_GPIO_PULL_NONE : updown; 146} 147 148samsung_gpio_pull_t s3c24xx_gpio_getpull_1up(struct samsung_gpio_chip *chip, 149 unsigned int off) 150{ 151 return s3c24xx_gpio_getpull_1(chip, off, S3C_GPIO_PULL_UP); 152} 153 154int s3c24xx_gpio_setpull_1up(struct samsung_gpio_chip *chip, 155 unsigned int off, samsung_gpio_pull_t pull) 156{ 157 return s3c24xx_gpio_setpull_1(chip, off, pull, S3C_GPIO_PULL_UP); 158} 159 160samsung_gpio_pull_t s3c24xx_gpio_getpull_1down(struct samsung_gpio_chip *chip, 161 unsigned int off) 162{ 163 return s3c24xx_gpio_getpull_1(chip, off, S3C_GPIO_PULL_DOWN); 164} 165 166int s3c24xx_gpio_setpull_1down(struct samsung_gpio_chip *chip, 167 unsigned int off, samsung_gpio_pull_t pull) 168{ 169 return s3c24xx_gpio_setpull_1(chip, off, pull, S3C_GPIO_PULL_DOWN); 170} 171 172static int exynos_gpio_setpull(struct samsung_gpio_chip *chip, 173 unsigned int off, samsung_gpio_pull_t pull) 174{ 175 if (pull == S3C_GPIO_PULL_UP) 176 pull = 3; 177 178 return samsung_gpio_setpull_updown(chip, off, pull); 179} 180 181static samsung_gpio_pull_t exynos_gpio_getpull(struct samsung_gpio_chip *chip, 182 unsigned int off) 183{ 184 samsung_gpio_pull_t pull; 185 186 pull = samsung_gpio_getpull_updown(chip, off); 187 188 if (pull == 3) 189 pull = S3C_GPIO_PULL_UP; 190 191 return pull; 192} 193 194/* 195 * samsung_gpio_setcfg_2bit - Samsung 2bit style GPIO configuration. 196 * @chip: The gpio chip that is being configured. 197 * @off: The offset for the GPIO being configured. 198 * @cfg: The configuration value to set. 199 * 200 * This helper deal with the GPIO cases where the control register 201 * has two bits of configuration per gpio, which have the following 202 * functions: 203 * 00 = input 204 * 01 = output 205 * 1x = special function 206 */ 207 208static int samsung_gpio_setcfg_2bit(struct samsung_gpio_chip *chip, 209 unsigned int off, unsigned int cfg) 210{ 211 void __iomem *reg = chip->base; 212 unsigned int shift = off * 2; 213 u32 con; 214 215 if (samsung_gpio_is_cfg_special(cfg)) { 216 cfg &= 0xf; 217 if (cfg > 3) 218 return -EINVAL; 219 220 cfg <<= shift; 221 } 222 223 con = __raw_readl(reg); 224 con &= ~(0x3 << shift); 225 con |= cfg; 226 __raw_writel(con, reg); 227 228 return 0; 229} 230 231/* 232 * samsung_gpio_getcfg_2bit - Samsung 2bit style GPIO configuration read. 233 * @chip: The gpio chip that is being configured. 234 * @off: The offset for the GPIO being configured. 235 * 236 * The reverse of samsung_gpio_setcfg_2bit(). Will return a value which 237 * could be directly passed back to samsung_gpio_setcfg_2bit(), from the 238 * S3C_GPIO_SPECIAL() macro. 239 */ 240 241static unsigned int samsung_gpio_getcfg_2bit(struct samsung_gpio_chip *chip, 242 unsigned int off) 243{ 244 u32 con; 245 246 con = __raw_readl(chip->base); 247 con >>= off * 2; 248 con &= 3; 249 250 /* this conversion works for IN and OUT as well as special mode */ 251 return S3C_GPIO_SPECIAL(con); 252} 253 254/* 255 * samsung_gpio_setcfg_4bit - Samsung 4bit single register GPIO config. 256 * @chip: The gpio chip that is being configured. 257 * @off: The offset for the GPIO being configured. 258 * @cfg: The configuration value to set. 259 * 260 * This helper deal with the GPIO cases where the control register has 4 bits 261 * of control per GPIO, generally in the form of: 262 * 0000 = Input 263 * 0001 = Output 264 * others = Special functions (dependent on bank) 265 * 266 * Note, since the code to deal with the case where there are two control 267 * registers instead of one, we do not have a separate set of functions for 268 * each case. 269 */ 270 271static int samsung_gpio_setcfg_4bit(struct samsung_gpio_chip *chip, 272 unsigned int off, unsigned int cfg) 273{ 274 void __iomem *reg = chip->base; 275 unsigned int shift = (off & 7) * 4; 276 u32 con; 277 278 if (off < 8 && chip->chip.ngpio > 8) 279 reg -= 4; 280 281 if (samsung_gpio_is_cfg_special(cfg)) { 282 cfg &= 0xf; 283 cfg <<= shift; 284 } 285 286 con = __raw_readl(reg); 287 con &= ~(0xf << shift); 288 con |= cfg; 289 __raw_writel(con, reg); 290 291 return 0; 292} 293 294/* 295 * samsung_gpio_getcfg_4bit - Samsung 4bit single register GPIO config read. 296 * @chip: The gpio chip that is being configured. 297 * @off: The offset for the GPIO being configured. 298 * 299 * The reverse of samsung_gpio_setcfg_4bit(), turning a gpio configuration 300 * register setting into a value the software can use, such as could be passed 301 * to samsung_gpio_setcfg_4bit(). 302 * 303 * @sa samsung_gpio_getcfg_2bit 304 */ 305 306static unsigned samsung_gpio_getcfg_4bit(struct samsung_gpio_chip *chip, 307 unsigned int off) 308{ 309 void __iomem *reg = chip->base; 310 unsigned int shift = (off & 7) * 4; 311 u32 con; 312 313 if (off < 8 && chip->chip.ngpio > 8) 314 reg -= 4; 315 316 con = __raw_readl(reg); 317 con >>= shift; 318 con &= 0xf; 319 320 /* this conversion works for IN and OUT as well as special mode */ 321 return S3C_GPIO_SPECIAL(con); 322} 323 324#ifdef CONFIG_PLAT_S3C24XX 325/* 326 * s3c24xx_gpio_setcfg_abank - S3C24XX style GPIO configuration (Bank A) 327 * @chip: The gpio chip that is being configured. 328 * @off: The offset for the GPIO being configured. 329 * @cfg: The configuration value to set. 330 * 331 * This helper deal with the GPIO cases where the control register 332 * has one bit of configuration for the gpio, where setting the bit 333 * means the pin is in special function mode and unset means output. 334 */ 335 336static int s3c24xx_gpio_setcfg_abank(struct samsung_gpio_chip *chip, 337 unsigned int off, unsigned int cfg) 338{ 339 void __iomem *reg = chip->base; 340 unsigned int shift = off; 341 u32 con; 342 343 if (samsung_gpio_is_cfg_special(cfg)) { 344 cfg &= 0xf; 345 346 /* Map output to 0, and SFN2 to 1 */ 347 cfg -= 1; 348 if (cfg > 1) 349 return -EINVAL; 350 351 cfg <<= shift; 352 } 353 354 con = __raw_readl(reg); 355 con &= ~(0x1 << shift); 356 con |= cfg; 357 __raw_writel(con, reg); 358 359 return 0; 360} 361 362/* 363 * s3c24xx_gpio_getcfg_abank - S3C24XX style GPIO configuration read (Bank A) 364 * @chip: The gpio chip that is being configured. 365 * @off: The offset for the GPIO being configured. 366 * 367 * The reverse of s3c24xx_gpio_setcfg_abank() turning an GPIO into a usable 368 * GPIO configuration value. 369 * 370 * @sa samsung_gpio_getcfg_2bit 371 * @sa samsung_gpio_getcfg_4bit 372 */ 373 374static unsigned s3c24xx_gpio_getcfg_abank(struct samsung_gpio_chip *chip, 375 unsigned int off) 376{ 377 u32 con; 378 379 con = __raw_readl(chip->base); 380 con >>= off; 381 con &= 1; 382 con++; 383 384 return S3C_GPIO_SFN(con); 385} 386#endif 387 388#if defined(CONFIG_CPU_S5P6440) || defined(CONFIG_CPU_S5P6450) 389static int s5p64x0_gpio_setcfg_rbank(struct samsung_gpio_chip *chip, 390 unsigned int off, unsigned int cfg) 391{ 392 void __iomem *reg = chip->base; 393 unsigned int shift; 394 u32 con; 395 396 switch (off) { 397 case 0: 398 case 1: 399 case 2: 400 case 3: 401 case 4: 402 case 5: 403 shift = (off & 7) * 4; 404 reg -= 4; 405 break; 406 case 6: 407 shift = ((off + 1) & 7) * 4; 408 reg -= 4; 409 default: 410 shift = ((off + 1) & 7) * 4; 411 break; 412 } 413 414 if (samsung_gpio_is_cfg_special(cfg)) { 415 cfg &= 0xf; 416 cfg <<= shift; 417 } 418 419 con = __raw_readl(reg); 420 con &= ~(0xf << shift); 421 con |= cfg; 422 __raw_writel(con, reg); 423 424 return 0; 425} 426#endif 427 428static void __init samsung_gpiolib_set_cfg(struct samsung_gpio_cfg *chipcfg, 429 int nr_chips) 430{ 431 for (; nr_chips > 0; nr_chips--, chipcfg++) { 432 if (!chipcfg->set_config) 433 chipcfg->set_config = samsung_gpio_setcfg_4bit; 434 if (!chipcfg->get_config) 435 chipcfg->get_config = samsung_gpio_getcfg_4bit; 436 if (!chipcfg->set_pull) 437 chipcfg->set_pull = samsung_gpio_setpull_updown; 438 if (!chipcfg->get_pull) 439 chipcfg->get_pull = samsung_gpio_getpull_updown; 440 } 441} 442 443struct samsung_gpio_cfg s3c24xx_gpiocfg_default = { 444 .set_config = samsung_gpio_setcfg_2bit, 445 .get_config = samsung_gpio_getcfg_2bit, 446}; 447 448#ifdef CONFIG_PLAT_S3C24XX 449static struct samsung_gpio_cfg s3c24xx_gpiocfg_banka = { 450 .set_config = s3c24xx_gpio_setcfg_abank, 451 .get_config = s3c24xx_gpio_getcfg_abank, 452}; 453#endif 454 455#if defined(CONFIG_ARCH_EXYNOS4) || defined(CONFIG_ARCH_EXYNOS5) 456static struct samsung_gpio_cfg exynos_gpio_cfg = { 457 .set_pull = exynos_gpio_setpull, 458 .get_pull = exynos_gpio_getpull, 459 .set_config = samsung_gpio_setcfg_4bit, 460 .get_config = samsung_gpio_getcfg_4bit, 461}; 462#endif 463 464#if defined(CONFIG_CPU_S5P6440) || defined(CONFIG_CPU_S5P6450) 465static struct samsung_gpio_cfg s5p64x0_gpio_cfg_rbank = { 466 .cfg_eint = 0x3, 467 .set_config = s5p64x0_gpio_setcfg_rbank, 468 .get_config = samsung_gpio_getcfg_4bit, 469 .set_pull = samsung_gpio_setpull_updown, 470 .get_pull = samsung_gpio_getpull_updown, 471}; 472#endif 473 474static struct samsung_gpio_cfg samsung_gpio_cfgs[] = { 475 [0] = { 476 .cfg_eint = 0x0, 477 }, 478 [1] = { 479 .cfg_eint = 0x3, 480 }, 481 [2] = { 482 .cfg_eint = 0x7, 483 }, 484 [3] = { 485 .cfg_eint = 0xF, 486 }, 487 [4] = { 488 .cfg_eint = 0x0, 489 .set_config = samsung_gpio_setcfg_2bit, 490 .get_config = samsung_gpio_getcfg_2bit, 491 }, 492 [5] = { 493 .cfg_eint = 0x2, 494 .set_config = samsung_gpio_setcfg_2bit, 495 .get_config = samsung_gpio_getcfg_2bit, 496 }, 497 [6] = { 498 .cfg_eint = 0x3, 499 .set_config = samsung_gpio_setcfg_2bit, 500 .get_config = samsung_gpio_getcfg_2bit, 501 }, 502 [7] = { 503 .set_config = samsung_gpio_setcfg_2bit, 504 .get_config = samsung_gpio_getcfg_2bit, 505 }, 506 [8] = { 507 .set_pull = exynos_gpio_setpull, 508 .get_pull = exynos_gpio_getpull, 509 }, 510 [9] = { 511 .cfg_eint = 0x3, 512 .set_pull = exynos_gpio_setpull, 513 .get_pull = exynos_gpio_getpull, 514 } 515}; 516 517/* 518 * Default routines for controlling GPIO, based on the original S3C24XX 519 * GPIO functions which deal with the case where each gpio bank of the 520 * chip is as following: 521 * 522 * base + 0x00: Control register, 2 bits per gpio 523 * gpio n: 2 bits starting at (2*n) 524 * 00 = input, 01 = output, others mean special-function 525 * base + 0x04: Data register, 1 bit per gpio 526 * bit n: data bit n 527*/ 528 529static int samsung_gpiolib_2bit_input(struct gpio_chip *chip, unsigned offset) 530{ 531 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 532 void __iomem *base = ourchip->base; 533 unsigned long flags; 534 unsigned long con; 535 536 samsung_gpio_lock(ourchip, flags); 537 538 con = __raw_readl(base + 0x00); 539 con &= ~(3 << (offset * 2)); 540 541 __raw_writel(con, base + 0x00); 542 543 samsung_gpio_unlock(ourchip, flags); 544 return 0; 545} 546 547static int samsung_gpiolib_2bit_output(struct gpio_chip *chip, 548 unsigned offset, int value) 549{ 550 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 551 void __iomem *base = ourchip->base; 552 unsigned long flags; 553 unsigned long dat; 554 unsigned long con; 555 556 samsung_gpio_lock(ourchip, flags); 557 558 dat = __raw_readl(base + 0x04); 559 dat &= ~(1 << offset); 560 if (value) 561 dat |= 1 << offset; 562 __raw_writel(dat, base + 0x04); 563 564 con = __raw_readl(base + 0x00); 565 con &= ~(3 << (offset * 2)); 566 con |= 1 << (offset * 2); 567 568 __raw_writel(con, base + 0x00); 569 __raw_writel(dat, base + 0x04); 570 571 samsung_gpio_unlock(ourchip, flags); 572 return 0; 573} 574 575/* 576 * The samsung_gpiolib_4bit routines are to control the gpio banks where 577 * the gpio configuration register (GPxCON) has 4 bits per GPIO, as the 578 * following example: 579 * 580 * base + 0x00: Control register, 4 bits per gpio 581 * gpio n: 4 bits starting at (4*n) 582 * 0000 = input, 0001 = output, others mean special-function 583 * base + 0x04: Data register, 1 bit per gpio 584 * bit n: data bit n 585 * 586 * Note, since the data register is one bit per gpio and is at base + 0x4 587 * we can use samsung_gpiolib_get and samsung_gpiolib_set to change the 588 * state of the output. 589 */ 590 591static int samsung_gpiolib_4bit_input(struct gpio_chip *chip, 592 unsigned int offset) 593{ 594 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 595 void __iomem *base = ourchip->base; 596 unsigned long con; 597 598 con = __raw_readl(base + GPIOCON_OFF); 599 con &= ~(0xf << con_4bit_shift(offset)); 600 __raw_writel(con, base + GPIOCON_OFF); 601 602 gpio_dbg("%s: %p: CON now %08lx\n", __func__, base, con); 603 604 return 0; 605} 606 607static int samsung_gpiolib_4bit_output(struct gpio_chip *chip, 608 unsigned int offset, int value) 609{ 610 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 611 void __iomem *base = ourchip->base; 612 unsigned long con; 613 unsigned long dat; 614 615 con = __raw_readl(base + GPIOCON_OFF); 616 con &= ~(0xf << con_4bit_shift(offset)); 617 con |= 0x1 << con_4bit_shift(offset); 618 619 dat = __raw_readl(base + GPIODAT_OFF); 620 621 if (value) 622 dat |= 1 << offset; 623 else 624 dat &= ~(1 << offset); 625 626 __raw_writel(dat, base + GPIODAT_OFF); 627 __raw_writel(con, base + GPIOCON_OFF); 628 __raw_writel(dat, base + GPIODAT_OFF); 629 630 gpio_dbg("%s: %p: CON %08lx, DAT %08lx\n", __func__, base, con, dat); 631 632 return 0; 633} 634 635/* 636 * The next set of routines are for the case where the GPIO configuration 637 * registers are 4 bits per GPIO but there is more than one register (the 638 * bank has more than 8 GPIOs. 639 * 640 * This case is the similar to the 4 bit case, but the registers are as 641 * follows: 642 * 643 * base + 0x00: Control register, 4 bits per gpio (lower 8 GPIOs) 644 * gpio n: 4 bits starting at (4*n) 645 * 0000 = input, 0001 = output, others mean special-function 646 * base + 0x04: Control register, 4 bits per gpio (up to 8 additions GPIOs) 647 * gpio n: 4 bits starting at (4*n) 648 * 0000 = input, 0001 = output, others mean special-function 649 * base + 0x08: Data register, 1 bit per gpio 650 * bit n: data bit n 651 * 652 * To allow us to use the samsung_gpiolib_get and samsung_gpiolib_set 653 * routines we store the 'base + 0x4' address so that these routines see 654 * the data register at ourchip->base + 0x04. 655 */ 656 657static int samsung_gpiolib_4bit2_input(struct gpio_chip *chip, 658 unsigned int offset) 659{ 660 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 661 void __iomem *base = ourchip->base; 662 void __iomem *regcon = base; 663 unsigned long con; 664 665 if (offset > 7) 666 offset -= 8; 667 else 668 regcon -= 4; 669 670 con = __raw_readl(regcon); 671 con &= ~(0xf << con_4bit_shift(offset)); 672 __raw_writel(con, regcon); 673 674 gpio_dbg("%s: %p: CON %08lx\n", __func__, base, con); 675 676 return 0; 677} 678 679static int samsung_gpiolib_4bit2_output(struct gpio_chip *chip, 680 unsigned int offset, int value) 681{ 682 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 683 void __iomem *base = ourchip->base; 684 void __iomem *regcon = base; 685 unsigned long con; 686 unsigned long dat; 687 unsigned con_offset = offset; 688 689 if (con_offset > 7) 690 con_offset -= 8; 691 else 692 regcon -= 4; 693 694 con = __raw_readl(regcon); 695 con &= ~(0xf << con_4bit_shift(con_offset)); 696 con |= 0x1 << con_4bit_shift(con_offset); 697 698 dat = __raw_readl(base + GPIODAT_OFF); 699 700 if (value) 701 dat |= 1 << offset; 702 else 703 dat &= ~(1 << offset); 704 705 __raw_writel(dat, base + GPIODAT_OFF); 706 __raw_writel(con, regcon); 707 __raw_writel(dat, base + GPIODAT_OFF); 708 709 gpio_dbg("%s: %p: CON %08lx, DAT %08lx\n", __func__, base, con, dat); 710 711 return 0; 712} 713 714#ifdef CONFIG_PLAT_S3C24XX 715/* The next set of routines are for the case of s3c24xx bank a */ 716 717static int s3c24xx_gpiolib_banka_input(struct gpio_chip *chip, unsigned offset) 718{ 719 return -EINVAL; 720} 721 722static int s3c24xx_gpiolib_banka_output(struct gpio_chip *chip, 723 unsigned offset, int value) 724{ 725 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 726 void __iomem *base = ourchip->base; 727 unsigned long flags; 728 unsigned long dat; 729 unsigned long con; 730 731 local_irq_save(flags); 732 733 con = __raw_readl(base + 0x00); 734 dat = __raw_readl(base + 0x04); 735 736 dat &= ~(1 << offset); 737 if (value) 738 dat |= 1 << offset; 739 740 __raw_writel(dat, base + 0x04); 741 742 con &= ~(1 << offset); 743 744 __raw_writel(con, base + 0x00); 745 __raw_writel(dat, base + 0x04); 746 747 local_irq_restore(flags); 748 return 0; 749} 750#endif 751 752/* The next set of routines are for the case of s5p64x0 bank r */ 753 754static int s5p64x0_gpiolib_rbank_input(struct gpio_chip *chip, 755 unsigned int offset) 756{ 757 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 758 void __iomem *base = ourchip->base; 759 void __iomem *regcon = base; 760 unsigned long con; 761 unsigned long flags; 762 763 switch (offset) { 764 case 6: 765 offset += 1; 766 case 0: 767 case 1: 768 case 2: 769 case 3: 770 case 4: 771 case 5: 772 regcon -= 4; 773 break; 774 default: 775 offset -= 7; 776 break; 777 } 778 779 samsung_gpio_lock(ourchip, flags); 780 781 con = __raw_readl(regcon); 782 con &= ~(0xf << con_4bit_shift(offset)); 783 __raw_writel(con, regcon); 784 785 samsung_gpio_unlock(ourchip, flags); 786 787 return 0; 788} 789 790static int s5p64x0_gpiolib_rbank_output(struct gpio_chip *chip, 791 unsigned int offset, int value) 792{ 793 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 794 void __iomem *base = ourchip->base; 795 void __iomem *regcon = base; 796 unsigned long con; 797 unsigned long dat; 798 unsigned long flags; 799 unsigned con_offset = offset; 800 801 switch (con_offset) { 802 case 6: 803 con_offset += 1; 804 case 0: 805 case 1: 806 case 2: 807 case 3: 808 case 4: 809 case 5: 810 regcon -= 4; 811 break; 812 default: 813 con_offset -= 7; 814 break; 815 } 816 817 samsung_gpio_lock(ourchip, flags); 818 819 con = __raw_readl(regcon); 820 con &= ~(0xf << con_4bit_shift(con_offset)); 821 con |= 0x1 << con_4bit_shift(con_offset); 822 823 dat = __raw_readl(base + GPIODAT_OFF); 824 if (value) 825 dat |= 1 << offset; 826 else 827 dat &= ~(1 << offset); 828 829 __raw_writel(con, regcon); 830 __raw_writel(dat, base + GPIODAT_OFF); 831 832 samsung_gpio_unlock(ourchip, flags); 833 834 return 0; 835} 836 837static void samsung_gpiolib_set(struct gpio_chip *chip, 838 unsigned offset, int value) 839{ 840 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 841 void __iomem *base = ourchip->base; 842 unsigned long flags; 843 unsigned long dat; 844 845 samsung_gpio_lock(ourchip, flags); 846 847 dat = __raw_readl(base + 0x04); 848 dat &= ~(1 << offset); 849 if (value) 850 dat |= 1 << offset; 851 __raw_writel(dat, base + 0x04); 852 853 samsung_gpio_unlock(ourchip, flags); 854} 855 856static int samsung_gpiolib_get(struct gpio_chip *chip, unsigned offset) 857{ 858 struct samsung_gpio_chip *ourchip = to_samsung_gpio(chip); 859 unsigned long val; 860 861 val = __raw_readl(ourchip->base + 0x04); 862 val >>= offset; 863 val &= 1; 864 865 return val; 866} 867 868/* 869 * CONFIG_S3C_GPIO_TRACK enables the tracking of the s3c specific gpios 870 * for use with the configuration calls, and other parts of the s3c gpiolib 871 * support code. 872 * 873 * Not all s3c support code will need this, as some configurations of cpu 874 * may only support one or two different configuration options and have an 875 * easy gpio to samsung_gpio_chip mapping function. If this is the case, then 876 * the machine support file should provide its own samsung_gpiolib_getchip() 877 * and any other necessary functions. 878 */ 879 880#ifdef CONFIG_S3C_GPIO_TRACK 881struct samsung_gpio_chip *s3c_gpios[S3C_GPIO_END]; 882 883static __init void s3c_gpiolib_track(struct samsung_gpio_chip *chip) 884{ 885 unsigned int gpn; 886 int i; 887 888 gpn = chip->chip.base; 889 for (i = 0; i < chip->chip.ngpio; i++, gpn++) { 890 BUG_ON(gpn >= ARRAY_SIZE(s3c_gpios)); 891 s3c_gpios[gpn] = chip; 892 } 893} 894#endif /* CONFIG_S3C_GPIO_TRACK */ 895 896/* 897 * samsung_gpiolib_add() - add the Samsung gpio_chip. 898 * @chip: The chip to register 899 * 900 * This is a wrapper to gpiochip_add() that takes our specific gpio chip 901 * information and makes the necessary alterations for the platform and 902 * notes the information for use with the configuration systems and any 903 * other parts of the system. 904 */ 905 906static void __init samsung_gpiolib_add(struct samsung_gpio_chip *chip) 907{ 908 struct gpio_chip *gc = &chip->chip; 909 int ret; 910 911 BUG_ON(!chip->base); 912 BUG_ON(!gc->label); 913 BUG_ON(!gc->ngpio); 914 915 spin_lock_init(&chip->lock); 916 917 if (!gc->direction_input) 918 gc->direction_input = samsung_gpiolib_2bit_input; 919 if (!gc->direction_output) 920 gc->direction_output = samsung_gpiolib_2bit_output; 921 if (!gc->set) 922 gc->set = samsung_gpiolib_set; 923 if (!gc->get) 924 gc->get = samsung_gpiolib_get; 925 926#ifdef CONFIG_PM 927 if (chip->pm != NULL) { 928 if (!chip->pm->save || !chip->pm->resume) 929 printk(KERN_ERR "gpio: %s has missing PM functions\n", 930 gc->label); 931 } else 932 printk(KERN_ERR "gpio: %s has no PM function\n", gc->label); 933#endif 934 935 /* gpiochip_add() prints own failure message on error. */ 936 ret = gpiochip_add(gc); 937 if (ret >= 0) 938 s3c_gpiolib_track(chip); 939} 940 941static void __init s3c24xx_gpiolib_add_chips(struct samsung_gpio_chip *chip, 942 int nr_chips, void __iomem *base) 943{ 944 int i; 945 struct gpio_chip *gc = &chip->chip; 946 947 for (i = 0 ; i < nr_chips; i++, chip++) { 948 /* skip banks not present on SoC */ 949 if (chip->chip.base >= S3C_GPIO_END) 950 continue; 951 952 if (!chip->config) 953 chip->config = &s3c24xx_gpiocfg_default; 954 if (!chip->pm) 955 chip->pm = __gpio_pm(&samsung_gpio_pm_2bit); 956 if ((base != NULL) && (chip->base == NULL)) 957 chip->base = base + ((i) * 0x10); 958 959 if (!gc->direction_input) 960 gc->direction_input = samsung_gpiolib_2bit_input; 961 if (!gc->direction_output) 962 gc->direction_output = samsung_gpiolib_2bit_output; 963 964 samsung_gpiolib_add(chip); 965 } 966} 967 968static void __init samsung_gpiolib_add_2bit_chips(struct samsung_gpio_chip *chip, 969 int nr_chips, void __iomem *base, 970 unsigned int offset) 971{ 972 int i; 973 974 for (i = 0 ; i < nr_chips; i++, chip++) { 975 chip->chip.direction_input = samsung_gpiolib_2bit_input; 976 chip->chip.direction_output = samsung_gpiolib_2bit_output; 977 978 if (!chip->config) 979 chip->config = &samsung_gpio_cfgs[7]; 980 if (!chip->pm) 981 chip->pm = __gpio_pm(&samsung_gpio_pm_2bit); 982 if ((base != NULL) && (chip->base == NULL)) 983 chip->base = base + ((i) * offset); 984 985 samsung_gpiolib_add(chip); 986 } 987} 988 989/* 990 * samsung_gpiolib_add_4bit_chips - 4bit single register GPIO config. 991 * @chip: The gpio chip that is being configured. 992 * @nr_chips: The no of chips (gpio ports) for the GPIO being configured. 993 * 994 * This helper deal with the GPIO cases where the control register has 4 bits 995 * of control per GPIO, generally in the form of: 996 * 0000 = Input 997 * 0001 = Output 998 * others = Special functions (dependent on bank) 999 * 1000 * Note, since the code to deal with the case where there are two control 1001 * registers instead of one, we do not have a separate set of function 1002 * (samsung_gpiolib_add_4bit2_chips)for each case. 1003 */ 1004 1005static void __init samsung_gpiolib_add_4bit_chips(struct samsung_gpio_chip *chip, 1006 int nr_chips, void __iomem *base) 1007{ 1008 int i; 1009 1010 for (i = 0 ; i < nr_chips; i++, chip++) { 1011 chip->chip.direction_input = samsung_gpiolib_4bit_input; 1012 chip->chip.direction_output = samsung_gpiolib_4bit_output; 1013 1014 if (!chip->config) 1015 chip->config = &samsung_gpio_cfgs[2]; 1016 if (!chip->pm) 1017 chip->pm = __gpio_pm(&samsung_gpio_pm_4bit); 1018 if ((base != NULL) && (chip->base == NULL)) 1019 chip->base = base + ((i) * 0x20); 1020 1021 samsung_gpiolib_add(chip); 1022 } 1023} 1024 1025static void __init samsung_gpiolib_add_4bit2_chips(struct samsung_gpio_chip *chip, 1026 int nr_chips) 1027{ 1028 for (; nr_chips > 0; nr_chips--, chip++) { 1029 chip->chip.direction_input = samsung_gpiolib_4bit2_input; 1030 chip->chip.direction_output = samsung_gpiolib_4bit2_output; 1031 1032 if (!chip->config) 1033 chip->config = &samsung_gpio_cfgs[2]; 1034 if (!chip->pm) 1035 chip->pm = __gpio_pm(&samsung_gpio_pm_4bit); 1036 1037 samsung_gpiolib_add(chip); 1038 } 1039} 1040 1041static void __init s5p64x0_gpiolib_add_rbank(struct samsung_gpio_chip *chip, 1042 int nr_chips) 1043{ 1044 for (; nr_chips > 0; nr_chips--, chip++) { 1045 chip->chip.direction_input = s5p64x0_gpiolib_rbank_input; 1046 chip->chip.direction_output = s5p64x0_gpiolib_rbank_output; 1047 1048 if (!chip->pm) 1049 chip->pm = __gpio_pm(&samsung_gpio_pm_4bit); 1050 1051 samsung_gpiolib_add(chip); 1052 } 1053} 1054 1055int samsung_gpiolib_to_irq(struct gpio_chip *chip, unsigned int offset) 1056{ 1057 struct samsung_gpio_chip *samsung_chip = container_of(chip, struct samsung_gpio_chip, chip); 1058 1059 return samsung_chip->irq_base + offset; 1060} 1061 1062#ifdef CONFIG_PLAT_S3C24XX 1063static int s3c24xx_gpiolib_fbank_to_irq(struct gpio_chip *chip, unsigned offset) 1064{ 1065 if (offset < 4) 1066 return IRQ_EINT0 + offset; 1067 1068 if (offset < 8) 1069 return IRQ_EINT4 + offset - 4; 1070 1071 return -EINVAL; 1072} 1073#endif 1074 1075#ifdef CONFIG_PLAT_S3C64XX 1076static int s3c64xx_gpiolib_mbank_to_irq(struct gpio_chip *chip, unsigned pin) 1077{ 1078 return pin < 5 ? IRQ_EINT(23) + pin : -ENXIO; 1079} 1080 1081static int s3c64xx_gpiolib_lbank_to_irq(struct gpio_chip *chip, unsigned pin) 1082{ 1083 return pin >= 8 ? IRQ_EINT(16) + pin - 8 : -ENXIO; 1084} 1085#endif 1086 1087struct samsung_gpio_chip s3c24xx_gpios[] = { 1088#ifdef CONFIG_PLAT_S3C24XX 1089 { 1090 .config = &s3c24xx_gpiocfg_banka, 1091 .chip = { 1092 .base = S3C2410_GPA(0), 1093 .owner = THIS_MODULE, 1094 .label = "GPIOA", 1095 .ngpio = 24, 1096 .direction_input = s3c24xx_gpiolib_banka_input, 1097 .direction_output = s3c24xx_gpiolib_banka_output, 1098 }, 1099 }, { 1100 .chip = { 1101 .base = S3C2410_GPB(0), 1102 .owner = THIS_MODULE, 1103 .label = "GPIOB", 1104 .ngpio = 16, 1105 }, 1106 }, { 1107 .chip = { 1108 .base = S3C2410_GPC(0), 1109 .owner = THIS_MODULE, 1110 .label = "GPIOC", 1111 .ngpio = 16, 1112 }, 1113 }, { 1114 .chip = { 1115 .base = S3C2410_GPD(0), 1116 .owner = THIS_MODULE, 1117 .label = "GPIOD", 1118 .ngpio = 16, 1119 }, 1120 }, { 1121 .chip = { 1122 .base = S3C2410_GPE(0), 1123 .label = "GPIOE", 1124 .owner = THIS_MODULE, 1125 .ngpio = 16, 1126 }, 1127 }, { 1128 .chip = { 1129 .base = S3C2410_GPF(0), 1130 .owner = THIS_MODULE, 1131 .label = "GPIOF", 1132 .ngpio = 8, 1133 .to_irq = s3c24xx_gpiolib_fbank_to_irq, 1134 }, 1135 }, { 1136 .irq_base = IRQ_EINT8, 1137 .chip = { 1138 .base = S3C2410_GPG(0), 1139 .owner = THIS_MODULE, 1140 .label = "GPIOG", 1141 .ngpio = 16, 1142 .to_irq = samsung_gpiolib_to_irq, 1143 }, 1144 }, { 1145 .chip = { 1146 .base = S3C2410_GPH(0), 1147 .owner = THIS_MODULE, 1148 .label = "GPIOH", 1149 .ngpio = 11, 1150 }, 1151 }, 1152 /* GPIOS for the S3C2443 and later devices. */ 1153 { 1154 .base = S3C2440_GPJCON, 1155 .chip = { 1156 .base = S3C2410_GPJ(0), 1157 .owner = THIS_MODULE, 1158 .label = "GPIOJ", 1159 .ngpio = 16, 1160 }, 1161 }, { 1162 .base = S3C2443_GPKCON, 1163 .chip = { 1164 .base = S3C2410_GPK(0), 1165 .owner = THIS_MODULE, 1166 .label = "GPIOK", 1167 .ngpio = 16, 1168 }, 1169 }, { 1170 .base = S3C2443_GPLCON, 1171 .chip = { 1172 .base = S3C2410_GPL(0), 1173 .owner = THIS_MODULE, 1174 .label = "GPIOL", 1175 .ngpio = 15, 1176 }, 1177 }, { 1178 .base = S3C2443_GPMCON, 1179 .chip = { 1180 .base = S3C2410_GPM(0), 1181 .owner = THIS_MODULE, 1182 .label = "GPIOM", 1183 .ngpio = 2, 1184 }, 1185 }, 1186#endif 1187}; 1188 1189/* 1190 * GPIO bank summary: 1191 * 1192 * Bank GPIOs Style SlpCon ExtInt Group 1193 * A 8 4Bit Yes 1 1194 * B 7 4Bit Yes 1 1195 * C 8 4Bit Yes 2 1196 * D 5 4Bit Yes 3 1197 * E 5 4Bit Yes None 1198 * F 16 2Bit Yes 4 [1] 1199 * G 7 4Bit Yes 5 1200 * H 10 4Bit[2] Yes 6 1201 * I 16 2Bit Yes None 1202 * J 12 2Bit Yes None 1203 * K 16 4Bit[2] No None 1204 * L 15 4Bit[2] No None 1205 * M 6 4Bit No IRQ_EINT 1206 * N 16 2Bit No IRQ_EINT 1207 * O 16 2Bit Yes 7 1208 * P 15 2Bit Yes 8 1209 * Q 9 2Bit Yes 9 1210 * 1211 * [1] BANKF pins 14,15 do not form part of the external interrupt sources 1212 * [2] BANK has two control registers, GPxCON0 and GPxCON1 1213 */ 1214 1215static struct samsung_gpio_chip s3c64xx_gpios_4bit[] = { 1216#ifdef CONFIG_PLAT_S3C64XX 1217 { 1218 .chip = { 1219 .base = S3C64XX_GPA(0), 1220 .ngpio = S3C64XX_GPIO_A_NR, 1221 .label = "GPA", 1222 }, 1223 }, { 1224 .chip = { 1225 .base = S3C64XX_GPB(0), 1226 .ngpio = S3C64XX_GPIO_B_NR, 1227 .label = "GPB", 1228 }, 1229 }, { 1230 .chip = { 1231 .base = S3C64XX_GPC(0), 1232 .ngpio = S3C64XX_GPIO_C_NR, 1233 .label = "GPC", 1234 }, 1235 }, { 1236 .chip = { 1237 .base = S3C64XX_GPD(0), 1238 .ngpio = S3C64XX_GPIO_D_NR, 1239 .label = "GPD", 1240 }, 1241 }, { 1242 .config = &samsung_gpio_cfgs[0], 1243 .chip = { 1244 .base = S3C64XX_GPE(0), 1245 .ngpio = S3C64XX_GPIO_E_NR, 1246 .label = "GPE", 1247 }, 1248 }, { 1249 .base = S3C64XX_GPG_BASE, 1250 .chip = { 1251 .base = S3C64XX_GPG(0), 1252 .ngpio = S3C64XX_GPIO_G_NR, 1253 .label = "GPG", 1254 }, 1255 }, { 1256 .base = S3C64XX_GPM_BASE, 1257 .config = &samsung_gpio_cfgs[1], 1258 .chip = { 1259 .base = S3C64XX_GPM(0), 1260 .ngpio = S3C64XX_GPIO_M_NR, 1261 .label = "GPM", 1262 .to_irq = s3c64xx_gpiolib_mbank_to_irq, 1263 }, 1264 }, 1265#endif 1266}; 1267 1268static struct samsung_gpio_chip s3c64xx_gpios_4bit2[] = { 1269#ifdef CONFIG_PLAT_S3C64XX 1270 { 1271 .base = S3C64XX_GPH_BASE + 0x4, 1272 .chip = { 1273 .base = S3C64XX_GPH(0), 1274 .ngpio = S3C64XX_GPIO_H_NR, 1275 .label = "GPH", 1276 }, 1277 }, { 1278 .base = S3C64XX_GPK_BASE + 0x4, 1279 .config = &samsung_gpio_cfgs[0], 1280 .chip = { 1281 .base = S3C64XX_GPK(0), 1282 .ngpio = S3C64XX_GPIO_K_NR, 1283 .label = "GPK", 1284 }, 1285 }, { 1286 .base = S3C64XX_GPL_BASE + 0x4, 1287 .config = &samsung_gpio_cfgs[1], 1288 .chip = { 1289 .base = S3C64XX_GPL(0), 1290 .ngpio = S3C64XX_GPIO_L_NR, 1291 .label = "GPL", 1292 .to_irq = s3c64xx_gpiolib_lbank_to_irq, 1293 }, 1294 }, 1295#endif 1296}; 1297 1298static struct samsung_gpio_chip s3c64xx_gpios_2bit[] = { 1299#ifdef CONFIG_PLAT_S3C64XX 1300 { 1301 .base = S3C64XX_GPF_BASE, 1302 .config = &samsung_gpio_cfgs[6], 1303 .chip = { 1304 .base = S3C64XX_GPF(0), 1305 .ngpio = S3C64XX_GPIO_F_NR, 1306 .label = "GPF", 1307 }, 1308 }, { 1309 .config = &samsung_gpio_cfgs[7], 1310 .chip = { 1311 .base = S3C64XX_GPI(0), 1312 .ngpio = S3C64XX_GPIO_I_NR, 1313 .label = "GPI", 1314 }, 1315 }, { 1316 .config = &samsung_gpio_cfgs[7], 1317 .chip = { 1318 .base = S3C64XX_GPJ(0), 1319 .ngpio = S3C64XX_GPIO_J_NR, 1320 .label = "GPJ", 1321 }, 1322 }, { 1323 .config = &samsung_gpio_cfgs[6], 1324 .chip = { 1325 .base = S3C64XX_GPO(0), 1326 .ngpio = S3C64XX_GPIO_O_NR, 1327 .label = "GPO", 1328 }, 1329 }, { 1330 .config = &samsung_gpio_cfgs[6], 1331 .chip = { 1332 .base = S3C64XX_GPP(0), 1333 .ngpio = S3C64XX_GPIO_P_NR, 1334 .label = "GPP", 1335 }, 1336 }, { 1337 .config = &samsung_gpio_cfgs[6], 1338 .chip = { 1339 .base = S3C64XX_GPQ(0), 1340 .ngpio = S3C64XX_GPIO_Q_NR, 1341 .label = "GPQ", 1342 }, 1343 }, { 1344 .base = S3C64XX_GPN_BASE, 1345 .irq_base = IRQ_EINT(0), 1346 .config = &samsung_gpio_cfgs[5], 1347 .chip = { 1348 .base = S3C64XX_GPN(0), 1349 .ngpio = S3C64XX_GPIO_N_NR, 1350 .label = "GPN", 1351 .to_irq = samsung_gpiolib_to_irq, 1352 }, 1353 }, 1354#endif 1355}; 1356 1357/* 1358 * S5P6440 GPIO bank summary: 1359 * 1360 * Bank GPIOs Style SlpCon ExtInt Group 1361 * A 6 4Bit Yes 1 1362 * B 7 4Bit Yes 1 1363 * C 8 4Bit Yes 2 1364 * F 2 2Bit Yes 4 [1] 1365 * G 7 4Bit Yes 5 1366 * H 10 4Bit[2] Yes 6 1367 * I 16 2Bit Yes None 1368 * J 12 2Bit Yes None 1369 * N 16 2Bit No IRQ_EINT 1370 * P 8 2Bit Yes 8 1371 * R 15 4Bit[2] Yes 8 1372 */ 1373 1374static struct samsung_gpio_chip s5p6440_gpios_4bit[] = { 1375#ifdef CONFIG_CPU_S5P6440 1376 { 1377 .chip = { 1378 .base = S5P6440_GPA(0), 1379 .ngpio = S5P6440_GPIO_A_NR, 1380 .label = "GPA", 1381 }, 1382 }, { 1383 .chip = { 1384 .base = S5P6440_GPB(0), 1385 .ngpio = S5P6440_GPIO_B_NR, 1386 .label = "GPB", 1387 }, 1388 }, { 1389 .chip = { 1390 .base = S5P6440_GPC(0), 1391 .ngpio = S5P6440_GPIO_C_NR, 1392 .label = "GPC", 1393 }, 1394 }, { 1395 .base = S5P64X0_GPG_BASE, 1396 .chip = { 1397 .base = S5P6440_GPG(0), 1398 .ngpio = S5P6440_GPIO_G_NR, 1399 .label = "GPG", 1400 }, 1401 }, 1402#endif 1403}; 1404 1405static struct samsung_gpio_chip s5p6440_gpios_4bit2[] = { 1406#ifdef CONFIG_CPU_S5P6440 1407 { 1408 .base = S5P64X0_GPH_BASE + 0x4, 1409 .chip = { 1410 .base = S5P6440_GPH(0), 1411 .ngpio = S5P6440_GPIO_H_NR, 1412 .label = "GPH", 1413 }, 1414 }, 1415#endif 1416}; 1417 1418static struct samsung_gpio_chip s5p6440_gpios_rbank[] = { 1419#ifdef CONFIG_CPU_S5P6440 1420 { 1421 .base = S5P64X0_GPR_BASE + 0x4, 1422 .config = &s5p64x0_gpio_cfg_rbank, 1423 .chip = { 1424 .base = S5P6440_GPR(0), 1425 .ngpio = S5P6440_GPIO_R_NR, 1426 .label = "GPR", 1427 }, 1428 }, 1429#endif 1430}; 1431 1432static struct samsung_gpio_chip s5p6440_gpios_2bit[] = { 1433#ifdef CONFIG_CPU_S5P6440 1434 { 1435 .base = S5P64X0_GPF_BASE, 1436 .config = &samsung_gpio_cfgs[6], 1437 .chip = { 1438 .base = S5P6440_GPF(0), 1439 .ngpio = S5P6440_GPIO_F_NR, 1440 .label = "GPF", 1441 }, 1442 }, { 1443 .base = S5P64X0_GPI_BASE, 1444 .config = &samsung_gpio_cfgs[4], 1445 .chip = { 1446 .base = S5P6440_GPI(0), 1447 .ngpio = S5P6440_GPIO_I_NR, 1448 .label = "GPI", 1449 }, 1450 }, { 1451 .base = S5P64X0_GPJ_BASE, 1452 .config = &samsung_gpio_cfgs[4], 1453 .chip = { 1454 .base = S5P6440_GPJ(0), 1455 .ngpio = S5P6440_GPIO_J_NR, 1456 .label = "GPJ", 1457 }, 1458 }, { 1459 .base = S5P64X0_GPN_BASE, 1460 .config = &samsung_gpio_cfgs[5], 1461 .chip = { 1462 .base = S5P6440_GPN(0), 1463 .ngpio = S5P6440_GPIO_N_NR, 1464 .label = "GPN", 1465 }, 1466 }, { 1467 .base = S5P64X0_GPP_BASE, 1468 .config = &samsung_gpio_cfgs[6], 1469 .chip = { 1470 .base = S5P6440_GPP(0), 1471 .ngpio = S5P6440_GPIO_P_NR, 1472 .label = "GPP", 1473 }, 1474 }, 1475#endif 1476}; 1477 1478/* 1479 * S5P6450 GPIO bank summary: 1480 * 1481 * Bank GPIOs Style SlpCon ExtInt Group 1482 * A 6 4Bit Yes 1 1483 * B 7 4Bit Yes 1 1484 * C 8 4Bit Yes 2 1485 * D 8 4Bit Yes None 1486 * F 2 2Bit Yes None 1487 * G 14 4Bit[2] Yes 5 1488 * H 10 4Bit[2] Yes 6 1489 * I 16 2Bit Yes None 1490 * J 12 2Bit Yes None 1491 * K 5 4Bit Yes None 1492 * N 16 2Bit No IRQ_EINT 1493 * P 11 2Bit Yes 8 1494 * Q 14 2Bit Yes None 1495 * R 15 4Bit[2] Yes None 1496 * S 8 2Bit Yes None 1497 * 1498 * [1] BANKF pins 14,15 do not form part of the external interrupt sources 1499 * [2] BANK has two control registers, GPxCON0 and GPxCON1 1500 */ 1501 1502static struct samsung_gpio_chip s5p6450_gpios_4bit[] = { 1503#ifdef CONFIG_CPU_S5P6450 1504 { 1505 .chip = { 1506 .base = S5P6450_GPA(0), 1507 .ngpio = S5P6450_GPIO_A_NR, 1508 .label = "GPA", 1509 }, 1510 }, { 1511 .chip = { 1512 .base = S5P6450_GPB(0), 1513 .ngpio = S5P6450_GPIO_B_NR, 1514 .label = "GPB", 1515 }, 1516 }, { 1517 .chip = { 1518 .base = S5P6450_GPC(0), 1519 .ngpio = S5P6450_GPIO_C_NR, 1520 .label = "GPC", 1521 }, 1522 }, { 1523 .chip = { 1524 .base = S5P6450_GPD(0), 1525 .ngpio = S5P6450_GPIO_D_NR, 1526 .label = "GPD", 1527 }, 1528 }, { 1529 .base = S5P6450_GPK_BASE, 1530 .chip = { 1531 .base = S5P6450_GPK(0), 1532 .ngpio = S5P6450_GPIO_K_NR, 1533 .label = "GPK", 1534 }, 1535 }, 1536#endif 1537}; 1538 1539static struct samsung_gpio_chip s5p6450_gpios_4bit2[] = { 1540#ifdef CONFIG_CPU_S5P6450 1541 { 1542 .base = S5P64X0_GPG_BASE + 0x4, 1543 .chip = { 1544 .base = S5P6450_GPG(0), 1545 .ngpio = S5P6450_GPIO_G_NR, 1546 .label = "GPG", 1547 }, 1548 }, { 1549 .base = S5P64X0_GPH_BASE + 0x4, 1550 .chip = { 1551 .base = S5P6450_GPH(0), 1552 .ngpio = S5P6450_GPIO_H_NR, 1553 .label = "GPH", 1554 }, 1555 }, 1556#endif 1557}; 1558 1559static struct samsung_gpio_chip s5p6450_gpios_rbank[] = { 1560#ifdef CONFIG_CPU_S5P6450 1561 { 1562 .base = S5P64X0_GPR_BASE + 0x4, 1563 .config = &s5p64x0_gpio_cfg_rbank, 1564 .chip = { 1565 .base = S5P6450_GPR(0), 1566 .ngpio = S5P6450_GPIO_R_NR, 1567 .label = "GPR", 1568 }, 1569 }, 1570#endif 1571}; 1572 1573static struct samsung_gpio_chip s5p6450_gpios_2bit[] = { 1574#ifdef CONFIG_CPU_S5P6450 1575 { 1576 .base = S5P64X0_GPF_BASE, 1577 .config = &samsung_gpio_cfgs[6], 1578 .chip = { 1579 .base = S5P6450_GPF(0), 1580 .ngpio = S5P6450_GPIO_F_NR, 1581 .label = "GPF", 1582 }, 1583 }, { 1584 .base = S5P64X0_GPI_BASE, 1585 .config = &samsung_gpio_cfgs[4], 1586 .chip = { 1587 .base = S5P6450_GPI(0), 1588 .ngpio = S5P6450_GPIO_I_NR, 1589 .label = "GPI", 1590 }, 1591 }, { 1592 .base = S5P64X0_GPJ_BASE, 1593 .config = &samsung_gpio_cfgs[4], 1594 .chip = { 1595 .base = S5P6450_GPJ(0), 1596 .ngpio = S5P6450_GPIO_J_NR, 1597 .label = "GPJ", 1598 }, 1599 }, { 1600 .base = S5P64X0_GPN_BASE, 1601 .config = &samsung_gpio_cfgs[5], 1602 .chip = { 1603 .base = S5P6450_GPN(0), 1604 .ngpio = S5P6450_GPIO_N_NR, 1605 .label = "GPN", 1606 }, 1607 }, { 1608 .base = S5P64X0_GPP_BASE, 1609 .config = &samsung_gpio_cfgs[6], 1610 .chip = { 1611 .base = S5P6450_GPP(0), 1612 .ngpio = S5P6450_GPIO_P_NR, 1613 .label = "GPP", 1614 }, 1615 }, { 1616 .base = S5P6450_GPQ_BASE, 1617 .config = &samsung_gpio_cfgs[5], 1618 .chip = { 1619 .base = S5P6450_GPQ(0), 1620 .ngpio = S5P6450_GPIO_Q_NR, 1621 .label = "GPQ", 1622 }, 1623 }, { 1624 .base = S5P6450_GPS_BASE, 1625 .config = &samsung_gpio_cfgs[6], 1626 .chip = { 1627 .base = S5P6450_GPS(0), 1628 .ngpio = S5P6450_GPIO_S_NR, 1629 .label = "GPS", 1630 }, 1631 }, 1632#endif 1633}; 1634 1635/* 1636 * S5PC100 GPIO bank summary: 1637 * 1638 * Bank GPIOs Style INT Type 1639 * A0 8 4Bit GPIO_INT0 1640 * A1 5 4Bit GPIO_INT1 1641 * B 8 4Bit GPIO_INT2 1642 * C 5 4Bit GPIO_INT3 1643 * D 7 4Bit GPIO_INT4 1644 * E0 8 4Bit GPIO_INT5 1645 * E1 6 4Bit GPIO_INT6 1646 * F0 8 4Bit GPIO_INT7 1647 * F1 8 4Bit GPIO_INT8 1648 * F2 8 4Bit GPIO_INT9 1649 * F3 4 4Bit GPIO_INT10 1650 * G0 8 4Bit GPIO_INT11 1651 * G1 3 4Bit GPIO_INT12 1652 * G2 7 4Bit GPIO_INT13 1653 * G3 7 4Bit GPIO_INT14 1654 * H0 8 4Bit WKUP_INT 1655 * H1 8 4Bit WKUP_INT 1656 * H2 8 4Bit WKUP_INT 1657 * H3 8 4Bit WKUP_INT 1658 * I 8 4Bit GPIO_INT15 1659 * J0 8 4Bit GPIO_INT16 1660 * J1 5 4Bit GPIO_INT17 1661 * J2 8 4Bit GPIO_INT18 1662 * J3 8 4Bit GPIO_INT19 1663 * J4 4 4Bit GPIO_INT20 1664 * K0 8 4Bit None 1665 * K1 6 4Bit None 1666 * K2 8 4Bit None 1667 * K3 8 4Bit None 1668 * L0 8 4Bit None 1669 * L1 8 4Bit None 1670 * L2 8 4Bit None 1671 * L3 8 4Bit None 1672 */ 1673 1674static struct samsung_gpio_chip s5pc100_gpios_4bit[] = { 1675#ifdef CONFIG_CPU_S5PC100 1676 { 1677 .chip = { 1678 .base = S5PC100_GPA0(0), 1679 .ngpio = S5PC100_GPIO_A0_NR, 1680 .label = "GPA0", 1681 }, 1682 }, { 1683 .chip = { 1684 .base = S5PC100_GPA1(0), 1685 .ngpio = S5PC100_GPIO_A1_NR, 1686 .label = "GPA1", 1687 }, 1688 }, { 1689 .chip = { 1690 .base = S5PC100_GPB(0), 1691 .ngpio = S5PC100_GPIO_B_NR, 1692 .label = "GPB", 1693 }, 1694 }, { 1695 .chip = { 1696 .base = S5PC100_GPC(0), 1697 .ngpio = S5PC100_GPIO_C_NR, 1698 .label = "GPC", 1699 }, 1700 }, { 1701 .chip = { 1702 .base = S5PC100_GPD(0), 1703 .ngpio = S5PC100_GPIO_D_NR, 1704 .label = "GPD", 1705 }, 1706 }, { 1707 .chip = { 1708 .base = S5PC100_GPE0(0), 1709 .ngpio = S5PC100_GPIO_E0_NR, 1710 .label = "GPE0", 1711 }, 1712 }, { 1713 .chip = { 1714 .base = S5PC100_GPE1(0), 1715 .ngpio = S5PC100_GPIO_E1_NR, 1716 .label = "GPE1", 1717 }, 1718 }, { 1719 .chip = { 1720 .base = S5PC100_GPF0(0), 1721 .ngpio = S5PC100_GPIO_F0_NR, 1722 .label = "GPF0", 1723 }, 1724 }, { 1725 .chip = { 1726 .base = S5PC100_GPF1(0), 1727 .ngpio = S5PC100_GPIO_F1_NR, 1728 .label = "GPF1", 1729 }, 1730 }, { 1731 .chip = { 1732 .base = S5PC100_GPF2(0), 1733 .ngpio = S5PC100_GPIO_F2_NR, 1734 .label = "GPF2", 1735 }, 1736 }, { 1737 .chip = { 1738 .base = S5PC100_GPF3(0), 1739 .ngpio = S5PC100_GPIO_F3_NR, 1740 .label = "GPF3", 1741 }, 1742 }, { 1743 .chip = { 1744 .base = S5PC100_GPG0(0), 1745 .ngpio = S5PC100_GPIO_G0_NR, 1746 .label = "GPG0", 1747 }, 1748 }, { 1749 .chip = { 1750 .base = S5PC100_GPG1(0), 1751 .ngpio = S5PC100_GPIO_G1_NR, 1752 .label = "GPG1", 1753 }, 1754 }, { 1755 .chip = { 1756 .base = S5PC100_GPG2(0), 1757 .ngpio = S5PC100_GPIO_G2_NR, 1758 .label = "GPG2", 1759 }, 1760 }, { 1761 .chip = { 1762 .base = S5PC100_GPG3(0), 1763 .ngpio = S5PC100_GPIO_G3_NR, 1764 .label = "GPG3", 1765 }, 1766 }, { 1767 .chip = { 1768 .base = S5PC100_GPI(0), 1769 .ngpio = S5PC100_GPIO_I_NR, 1770 .label = "GPI", 1771 }, 1772 }, { 1773 .chip = { 1774 .base = S5PC100_GPJ0(0), 1775 .ngpio = S5PC100_GPIO_J0_NR, 1776 .label = "GPJ0", 1777 }, 1778 }, { 1779 .chip = { 1780 .base = S5PC100_GPJ1(0), 1781 .ngpio = S5PC100_GPIO_J1_NR, 1782 .label = "GPJ1", 1783 }, 1784 }, { 1785 .chip = { 1786 .base = S5PC100_GPJ2(0), 1787 .ngpio = S5PC100_GPIO_J2_NR, 1788 .label = "GPJ2", 1789 }, 1790 }, { 1791 .chip = { 1792 .base = S5PC100_GPJ3(0), 1793 .ngpio = S5PC100_GPIO_J3_NR, 1794 .label = "GPJ3", 1795 }, 1796 }, { 1797 .chip = { 1798 .base = S5PC100_GPJ4(0), 1799 .ngpio = S5PC100_GPIO_J4_NR, 1800 .label = "GPJ4", 1801 }, 1802 }, { 1803 .chip = { 1804 .base = S5PC100_GPK0(0), 1805 .ngpio = S5PC100_GPIO_K0_NR, 1806 .label = "GPK0", 1807 }, 1808 }, { 1809 .chip = { 1810 .base = S5PC100_GPK1(0), 1811 .ngpio = S5PC100_GPIO_K1_NR, 1812 .label = "GPK1", 1813 }, 1814 }, { 1815 .chip = { 1816 .base = S5PC100_GPK2(0), 1817 .ngpio = S5PC100_GPIO_K2_NR, 1818 .label = "GPK2", 1819 }, 1820 }, { 1821 .chip = { 1822 .base = S5PC100_GPK3(0), 1823 .ngpio = S5PC100_GPIO_K3_NR, 1824 .label = "GPK3", 1825 }, 1826 }, { 1827 .chip = { 1828 .base = S5PC100_GPL0(0), 1829 .ngpio = S5PC100_GPIO_L0_NR, 1830 .label = "GPL0", 1831 }, 1832 }, { 1833 .chip = { 1834 .base = S5PC100_GPL1(0), 1835 .ngpio = S5PC100_GPIO_L1_NR, 1836 .label = "GPL1", 1837 }, 1838 }, { 1839 .chip = { 1840 .base = S5PC100_GPL2(0), 1841 .ngpio = S5PC100_GPIO_L2_NR, 1842 .label = "GPL2", 1843 }, 1844 }, { 1845 .chip = { 1846 .base = S5PC100_GPL3(0), 1847 .ngpio = S5PC100_GPIO_L3_NR, 1848 .label = "GPL3", 1849 }, 1850 }, { 1851 .chip = { 1852 .base = S5PC100_GPL4(0), 1853 .ngpio = S5PC100_GPIO_L4_NR, 1854 .label = "GPL4", 1855 }, 1856 }, { 1857 .base = (S5P_VA_GPIO + 0xC00), 1858 .irq_base = IRQ_EINT(0), 1859 .chip = { 1860 .base = S5PC100_GPH0(0), 1861 .ngpio = S5PC100_GPIO_H0_NR, 1862 .label = "GPH0", 1863 .to_irq = samsung_gpiolib_to_irq, 1864 }, 1865 }, { 1866 .base = (S5P_VA_GPIO + 0xC20), 1867 .irq_base = IRQ_EINT(8), 1868 .chip = { 1869 .base = S5PC100_GPH1(0), 1870 .ngpio = S5PC100_GPIO_H1_NR, 1871 .label = "GPH1", 1872 .to_irq = samsung_gpiolib_to_irq, 1873 }, 1874 }, { 1875 .base = (S5P_VA_GPIO + 0xC40), 1876 .irq_base = IRQ_EINT(16), 1877 .chip = { 1878 .base = S5PC100_GPH2(0), 1879 .ngpio = S5PC100_GPIO_H2_NR, 1880 .label = "GPH2", 1881 .to_irq = samsung_gpiolib_to_irq, 1882 }, 1883 }, { 1884 .base = (S5P_VA_GPIO + 0xC60), 1885 .irq_base = IRQ_EINT(24), 1886 .chip = { 1887 .base = S5PC100_GPH3(0), 1888 .ngpio = S5PC100_GPIO_H3_NR, 1889 .label = "GPH3", 1890 .to_irq = samsung_gpiolib_to_irq, 1891 }, 1892 }, 1893#endif 1894}; 1895 1896/* 1897 * Followings are the gpio banks in S5PV210/S5PC110 1898 * 1899 * The 'config' member when left to NULL, is initialized to the default 1900 * structure samsung_gpio_cfgs[3] in the init function below. 1901 * 1902 * The 'base' member is also initialized in the init function below. 1903 * Note: The initialization of 'base' member of samsung_gpio_chip structure 1904 * uses the above macro and depends on the banks being listed in order here. 1905 */ 1906 1907static struct samsung_gpio_chip s5pv210_gpios_4bit[] = { 1908#ifdef CONFIG_CPU_S5PV210 1909 { 1910 .chip = { 1911 .base = S5PV210_GPA0(0), 1912 .ngpio = S5PV210_GPIO_A0_NR, 1913 .label = "GPA0", 1914 }, 1915 }, { 1916 .chip = { 1917 .base = S5PV210_GPA1(0), 1918 .ngpio = S5PV210_GPIO_A1_NR, 1919 .label = "GPA1", 1920 }, 1921 }, { 1922 .chip = { 1923 .base = S5PV210_GPB(0), 1924 .ngpio = S5PV210_GPIO_B_NR, 1925 .label = "GPB", 1926 }, 1927 }, { 1928 .chip = { 1929 .base = S5PV210_GPC0(0), 1930 .ngpio = S5PV210_GPIO_C0_NR, 1931 .label = "GPC0", 1932 }, 1933 }, { 1934 .chip = { 1935 .base = S5PV210_GPC1(0), 1936 .ngpio = S5PV210_GPIO_C1_NR, 1937 .label = "GPC1", 1938 }, 1939 }, { 1940 .chip = { 1941 .base = S5PV210_GPD0(0), 1942 .ngpio = S5PV210_GPIO_D0_NR, 1943 .label = "GPD0", 1944 }, 1945 }, { 1946 .chip = { 1947 .base = S5PV210_GPD1(0), 1948 .ngpio = S5PV210_GPIO_D1_NR, 1949 .label = "GPD1", 1950 }, 1951 }, { 1952 .chip = { 1953 .base = S5PV210_GPE0(0), 1954 .ngpio = S5PV210_GPIO_E0_NR, 1955 .label = "GPE0", 1956 }, 1957 }, { 1958 .chip = { 1959 .base = S5PV210_GPE1(0), 1960 .ngpio = S5PV210_GPIO_E1_NR, 1961 .label = "GPE1", 1962 }, 1963 }, { 1964 .chip = { 1965 .base = S5PV210_GPF0(0), 1966 .ngpio = S5PV210_GPIO_F0_NR, 1967 .label = "GPF0", 1968 }, 1969 }, { 1970 .chip = { 1971 .base = S5PV210_GPF1(0), 1972 .ngpio = S5PV210_GPIO_F1_NR, 1973 .label = "GPF1", 1974 }, 1975 }, { 1976 .chip = { 1977 .base = S5PV210_GPF2(0), 1978 .ngpio = S5PV210_GPIO_F2_NR, 1979 .label = "GPF2", 1980 }, 1981 }, { 1982 .chip = { 1983 .base = S5PV210_GPF3(0), 1984 .ngpio = S5PV210_GPIO_F3_NR, 1985 .label = "GPF3", 1986 }, 1987 }, { 1988 .chip = { 1989 .base = S5PV210_GPG0(0), 1990 .ngpio = S5PV210_GPIO_G0_NR, 1991 .label = "GPG0", 1992 }, 1993 }, { 1994 .chip = { 1995 .base = S5PV210_GPG1(0), 1996 .ngpio = S5PV210_GPIO_G1_NR, 1997 .label = "GPG1", 1998 }, 1999 }, { 2000 .chip = { 2001 .base = S5PV210_GPG2(0), 2002 .ngpio = S5PV210_GPIO_G2_NR, 2003 .label = "GPG2", 2004 }, 2005 }, { 2006 .chip = { 2007 .base = S5PV210_GPG3(0), 2008 .ngpio = S5PV210_GPIO_G3_NR, 2009 .label = "GPG3", 2010 }, 2011 }, { 2012 .chip = { 2013 .base = S5PV210_GPI(0), 2014 .ngpio = S5PV210_GPIO_I_NR, 2015 .label = "GPI", 2016 }, 2017 }, { 2018 .chip = { 2019 .base = S5PV210_GPJ0(0), 2020 .ngpio = S5PV210_GPIO_J0_NR, 2021 .label = "GPJ0", 2022 }, 2023 }, { 2024 .chip = { 2025 .base = S5PV210_GPJ1(0), 2026 .ngpio = S5PV210_GPIO_J1_NR, 2027 .label = "GPJ1", 2028 }, 2029 }, { 2030 .chip = { 2031 .base = S5PV210_GPJ2(0), 2032 .ngpio = S5PV210_GPIO_J2_NR, 2033 .label = "GPJ2", 2034 }, 2035 }, { 2036 .chip = { 2037 .base = S5PV210_GPJ3(0), 2038 .ngpio = S5PV210_GPIO_J3_NR, 2039 .label = "GPJ3", 2040 }, 2041 }, { 2042 .chip = { 2043 .base = S5PV210_GPJ4(0), 2044 .ngpio = S5PV210_GPIO_J4_NR, 2045 .label = "GPJ4", 2046 }, 2047 }, { 2048 .chip = { 2049 .base = S5PV210_MP01(0), 2050 .ngpio = S5PV210_GPIO_MP01_NR, 2051 .label = "MP01", 2052 }, 2053 }, { 2054 .chip = { 2055 .base = S5PV210_MP02(0), 2056 .ngpio = S5PV210_GPIO_MP02_NR, 2057 .label = "MP02", 2058 }, 2059 }, { 2060 .chip = { 2061 .base = S5PV210_MP03(0), 2062 .ngpio = S5PV210_GPIO_MP03_NR, 2063 .label = "MP03", 2064 }, 2065 }, { 2066 .chip = { 2067 .base = S5PV210_MP04(0), 2068 .ngpio = S5PV210_GPIO_MP04_NR, 2069 .label = "MP04", 2070 }, 2071 }, { 2072 .chip = { 2073 .base = S5PV210_MP05(0), 2074 .ngpio = S5PV210_GPIO_MP05_NR, 2075 .label = "MP05", 2076 }, 2077 }, { 2078 .base = (S5P_VA_GPIO + 0xC00), 2079 .irq_base = IRQ_EINT(0), 2080 .chip = { 2081 .base = S5PV210_GPH0(0), 2082 .ngpio = S5PV210_GPIO_H0_NR, 2083 .label = "GPH0", 2084 .to_irq = samsung_gpiolib_to_irq, 2085 }, 2086 }, { 2087 .base = (S5P_VA_GPIO + 0xC20), 2088 .irq_base = IRQ_EINT(8), 2089 .chip = { 2090 .base = S5PV210_GPH1(0), 2091 .ngpio = S5PV210_GPIO_H1_NR, 2092 .label = "GPH1", 2093 .to_irq = samsung_gpiolib_to_irq, 2094 }, 2095 }, { 2096 .base = (S5P_VA_GPIO + 0xC40), 2097 .irq_base = IRQ_EINT(16), 2098 .chip = { 2099 .base = S5PV210_GPH2(0), 2100 .ngpio = S5PV210_GPIO_H2_NR, 2101 .label = "GPH2", 2102 .to_irq = samsung_gpiolib_to_irq, 2103 }, 2104 }, { 2105 .base = (S5P_VA_GPIO + 0xC60), 2106 .irq_base = IRQ_EINT(24), 2107 .chip = { 2108 .base = S5PV210_GPH3(0), 2109 .ngpio = S5PV210_GPIO_H3_NR, 2110 .label = "GPH3", 2111 .to_irq = samsung_gpiolib_to_irq, 2112 }, 2113 }, 2114#endif 2115}; 2116 2117/* 2118 * Followings are the gpio banks in EXYNOS SoCs 2119 * 2120 * The 'config' member when left to NULL, is initialized to the default 2121 * structure exynos_gpio_cfg in the init function below. 2122 * 2123 * The 'base' member is also initialized in the init function below. 2124 * Note: The initialization of 'base' member of samsung_gpio_chip structure 2125 * uses the above macro and depends on the banks being listed in order here. 2126 */ 2127 2128#ifdef CONFIG_ARCH_EXYNOS4 2129static struct samsung_gpio_chip exynos4_gpios_1[] = { 2130 { 2131 .chip = { 2132 .base = EXYNOS4_GPA0(0), 2133 .ngpio = EXYNOS4_GPIO_A0_NR, 2134 .label = "GPA0", 2135 }, 2136 }, { 2137 .chip = { 2138 .base = EXYNOS4_GPA1(0), 2139 .ngpio = EXYNOS4_GPIO_A1_NR, 2140 .label = "GPA1", 2141 }, 2142 }, { 2143 .chip = { 2144 .base = EXYNOS4_GPB(0), 2145 .ngpio = EXYNOS4_GPIO_B_NR, 2146 .label = "GPB", 2147 }, 2148 }, { 2149 .chip = { 2150 .base = EXYNOS4_GPC0(0), 2151 .ngpio = EXYNOS4_GPIO_C0_NR, 2152 .label = "GPC0", 2153 }, 2154 }, { 2155 .chip = { 2156 .base = EXYNOS4_GPC1(0), 2157 .ngpio = EXYNOS4_GPIO_C1_NR, 2158 .label = "GPC1", 2159 }, 2160 }, { 2161 .chip = { 2162 .base = EXYNOS4_GPD0(0), 2163 .ngpio = EXYNOS4_GPIO_D0_NR, 2164 .label = "GPD0", 2165 }, 2166 }, { 2167 .chip = { 2168 .base = EXYNOS4_GPD1(0), 2169 .ngpio = EXYNOS4_GPIO_D1_NR, 2170 .label = "GPD1", 2171 }, 2172 }, { 2173 .chip = { 2174 .base = EXYNOS4_GPE0(0), 2175 .ngpio = EXYNOS4_GPIO_E0_NR, 2176 .label = "GPE0", 2177 }, 2178 }, { 2179 .chip = { 2180 .base = EXYNOS4_GPE1(0), 2181 .ngpio = EXYNOS4_GPIO_E1_NR, 2182 .label = "GPE1", 2183 }, 2184 }, { 2185 .chip = { 2186 .base = EXYNOS4_GPE2(0), 2187 .ngpio = EXYNOS4_GPIO_E2_NR, 2188 .label = "GPE2", 2189 }, 2190 }, { 2191 .chip = { 2192 .base = EXYNOS4_GPE3(0), 2193 .ngpio = EXYNOS4_GPIO_E3_NR, 2194 .label = "GPE3", 2195 }, 2196 }, { 2197 .chip = { 2198 .base = EXYNOS4_GPE4(0), 2199 .ngpio = EXYNOS4_GPIO_E4_NR, 2200 .label = "GPE4", 2201 }, 2202 }, { 2203 .chip = { 2204 .base = EXYNOS4_GPF0(0), 2205 .ngpio = EXYNOS4_GPIO_F0_NR, 2206 .label = "GPF0", 2207 }, 2208 }, { 2209 .chip = { 2210 .base = EXYNOS4_GPF1(0), 2211 .ngpio = EXYNOS4_GPIO_F1_NR, 2212 .label = "GPF1", 2213 }, 2214 }, { 2215 .chip = { 2216 .base = EXYNOS4_GPF2(0), 2217 .ngpio = EXYNOS4_GPIO_F2_NR, 2218 .label = "GPF2", 2219 }, 2220 }, { 2221 .chip = { 2222 .base = EXYNOS4_GPF3(0), 2223 .ngpio = EXYNOS4_GPIO_F3_NR, 2224 .label = "GPF3", 2225 }, 2226 }, 2227}; 2228#endif 2229 2230#ifdef CONFIG_ARCH_EXYNOS4 2231static struct samsung_gpio_chip exynos4_gpios_2[] = { 2232 { 2233 .chip = { 2234 .base = EXYNOS4_GPJ0(0), 2235 .ngpio = EXYNOS4_GPIO_J0_NR, 2236 .label = "GPJ0", 2237 }, 2238 }, { 2239 .chip = { 2240 .base = EXYNOS4_GPJ1(0), 2241 .ngpio = EXYNOS4_GPIO_J1_NR, 2242 .label = "GPJ1", 2243 }, 2244 }, { 2245 .chip = { 2246 .base = EXYNOS4_GPK0(0), 2247 .ngpio = EXYNOS4_GPIO_K0_NR, 2248 .label = "GPK0", 2249 }, 2250 }, { 2251 .chip = { 2252 .base = EXYNOS4_GPK1(0), 2253 .ngpio = EXYNOS4_GPIO_K1_NR, 2254 .label = "GPK1", 2255 }, 2256 }, { 2257 .chip = { 2258 .base = EXYNOS4_GPK2(0), 2259 .ngpio = EXYNOS4_GPIO_K2_NR, 2260 .label = "GPK2", 2261 }, 2262 }, { 2263 .chip = { 2264 .base = EXYNOS4_GPK3(0), 2265 .ngpio = EXYNOS4_GPIO_K3_NR, 2266 .label = "GPK3", 2267 }, 2268 }, { 2269 .chip = { 2270 .base = EXYNOS4_GPL0(0), 2271 .ngpio = EXYNOS4_GPIO_L0_NR, 2272 .label = "GPL0", 2273 }, 2274 }, { 2275 .chip = { 2276 .base = EXYNOS4_GPL1(0), 2277 .ngpio = EXYNOS4_GPIO_L1_NR, 2278 .label = "GPL1", 2279 }, 2280 }, { 2281 .chip = { 2282 .base = EXYNOS4_GPL2(0), 2283 .ngpio = EXYNOS4_GPIO_L2_NR, 2284 .label = "GPL2", 2285 }, 2286 }, { 2287 .config = &samsung_gpio_cfgs[8], 2288 .chip = { 2289 .base = EXYNOS4_GPY0(0), 2290 .ngpio = EXYNOS4_GPIO_Y0_NR, 2291 .label = "GPY0", 2292 }, 2293 }, { 2294 .config = &samsung_gpio_cfgs[8], 2295 .chip = { 2296 .base = EXYNOS4_GPY1(0), 2297 .ngpio = EXYNOS4_GPIO_Y1_NR, 2298 .label = "GPY1", 2299 }, 2300 }, { 2301 .config = &samsung_gpio_cfgs[8], 2302 .chip = { 2303 .base = EXYNOS4_GPY2(0), 2304 .ngpio = EXYNOS4_GPIO_Y2_NR, 2305 .label = "GPY2", 2306 }, 2307 }, { 2308 .config = &samsung_gpio_cfgs[8], 2309 .chip = { 2310 .base = EXYNOS4_GPY3(0), 2311 .ngpio = EXYNOS4_GPIO_Y3_NR, 2312 .label = "GPY3", 2313 }, 2314 }, { 2315 .config = &samsung_gpio_cfgs[8], 2316 .chip = { 2317 .base = EXYNOS4_GPY4(0), 2318 .ngpio = EXYNOS4_GPIO_Y4_NR, 2319 .label = "GPY4", 2320 }, 2321 }, { 2322 .config = &samsung_gpio_cfgs[8], 2323 .chip = { 2324 .base = EXYNOS4_GPY5(0), 2325 .ngpio = EXYNOS4_GPIO_Y5_NR, 2326 .label = "GPY5", 2327 }, 2328 }, { 2329 .config = &samsung_gpio_cfgs[8], 2330 .chip = { 2331 .base = EXYNOS4_GPY6(0), 2332 .ngpio = EXYNOS4_GPIO_Y6_NR, 2333 .label = "GPY6", 2334 }, 2335 }, { 2336 .config = &samsung_gpio_cfgs[9], 2337 .irq_base = IRQ_EINT(0), 2338 .chip = { 2339 .base = EXYNOS4_GPX0(0), 2340 .ngpio = EXYNOS4_GPIO_X0_NR, 2341 .label = "GPX0", 2342 .to_irq = samsung_gpiolib_to_irq, 2343 }, 2344 }, { 2345 .config = &samsung_gpio_cfgs[9], 2346 .irq_base = IRQ_EINT(8), 2347 .chip = { 2348 .base = EXYNOS4_GPX1(0), 2349 .ngpio = EXYNOS4_GPIO_X1_NR, 2350 .label = "GPX1", 2351 .to_irq = samsung_gpiolib_to_irq, 2352 }, 2353 }, { 2354 .config = &samsung_gpio_cfgs[9], 2355 .irq_base = IRQ_EINT(16), 2356 .chip = { 2357 .base = EXYNOS4_GPX2(0), 2358 .ngpio = EXYNOS4_GPIO_X2_NR, 2359 .label = "GPX2", 2360 .to_irq = samsung_gpiolib_to_irq, 2361 }, 2362 }, { 2363 .config = &samsung_gpio_cfgs[9], 2364 .irq_base = IRQ_EINT(24), 2365 .chip = { 2366 .base = EXYNOS4_GPX3(0), 2367 .ngpio = EXYNOS4_GPIO_X3_NR, 2368 .label = "GPX3", 2369 .to_irq = samsung_gpiolib_to_irq, 2370 }, 2371 }, 2372}; 2373#endif 2374 2375#ifdef CONFIG_ARCH_EXYNOS4 2376static struct samsung_gpio_chip exynos4_gpios_3[] = { 2377 { 2378 .chip = { 2379 .base = EXYNOS4_GPZ(0), 2380 .ngpio = EXYNOS4_GPIO_Z_NR, 2381 .label = "GPZ", 2382 }, 2383 }, 2384}; 2385#endif 2386 2387#ifdef CONFIG_ARCH_EXYNOS5 2388static struct samsung_gpio_chip exynos5_gpios_1[] = { 2389 { 2390 .chip = { 2391 .base = EXYNOS5_GPA0(0), 2392 .ngpio = EXYNOS5_GPIO_A0_NR, 2393 .label = "GPA0", 2394 }, 2395 }, { 2396 .chip = { 2397 .base = EXYNOS5_GPA1(0), 2398 .ngpio = EXYNOS5_GPIO_A1_NR, 2399 .label = "GPA1", 2400 }, 2401 }, { 2402 .chip = { 2403 .base = EXYNOS5_GPA2(0), 2404 .ngpio = EXYNOS5_GPIO_A2_NR, 2405 .label = "GPA2", 2406 }, 2407 }, { 2408 .chip = { 2409 .base = EXYNOS5_GPB0(0), 2410 .ngpio = EXYNOS5_GPIO_B0_NR, 2411 .label = "GPB0", 2412 }, 2413 }, { 2414 .chip = { 2415 .base = EXYNOS5_GPB1(0), 2416 .ngpio = EXYNOS5_GPIO_B1_NR, 2417 .label = "GPB1", 2418 }, 2419 }, { 2420 .chip = { 2421 .base = EXYNOS5_GPB2(0), 2422 .ngpio = EXYNOS5_GPIO_B2_NR, 2423 .label = "GPB2", 2424 }, 2425 }, { 2426 .chip = { 2427 .base = EXYNOS5_GPB3(0), 2428 .ngpio = EXYNOS5_GPIO_B3_NR, 2429 .label = "GPB3", 2430 }, 2431 }, { 2432 .chip = { 2433 .base = EXYNOS5_GPC0(0), 2434 .ngpio = EXYNOS5_GPIO_C0_NR, 2435 .label = "GPC0", 2436 }, 2437 }, { 2438 .chip = { 2439 .base = EXYNOS5_GPC1(0), 2440 .ngpio = EXYNOS5_GPIO_C1_NR, 2441 .label = "GPC1", 2442 }, 2443 }, { 2444 .chip = { 2445 .base = EXYNOS5_GPC2(0), 2446 .ngpio = EXYNOS5_GPIO_C2_NR, 2447 .label = "GPC2", 2448 }, 2449 }, { 2450 .chip = { 2451 .base = EXYNOS5_GPC3(0), 2452 .ngpio = EXYNOS5_GPIO_C3_NR, 2453 .label = "GPC3", 2454 }, 2455 }, { 2456 .chip = { 2457 .base = EXYNOS5_GPD0(0), 2458 .ngpio = EXYNOS5_GPIO_D0_NR, 2459 .label = "GPD0", 2460 }, 2461 }, { 2462 .chip = { 2463 .base = EXYNOS5_GPD1(0), 2464 .ngpio = EXYNOS5_GPIO_D1_NR, 2465 .label = "GPD1", 2466 }, 2467 }, { 2468 .chip = { 2469 .base = EXYNOS5_GPY0(0), 2470 .ngpio = EXYNOS5_GPIO_Y0_NR, 2471 .label = "GPY0", 2472 }, 2473 }, { 2474 .chip = { 2475 .base = EXYNOS5_GPY1(0), 2476 .ngpio = EXYNOS5_GPIO_Y1_NR, 2477 .label = "GPY1", 2478 }, 2479 }, { 2480 .chip = { 2481 .base = EXYNOS5_GPY2(0), 2482 .ngpio = EXYNOS5_GPIO_Y2_NR, 2483 .label = "GPY2", 2484 }, 2485 }, { 2486 .chip = { 2487 .base = EXYNOS5_GPY3(0), 2488 .ngpio = EXYNOS5_GPIO_Y3_NR, 2489 .label = "GPY3", 2490 }, 2491 }, { 2492 .chip = { 2493 .base = EXYNOS5_GPY4(0), 2494 .ngpio = EXYNOS5_GPIO_Y4_NR, 2495 .label = "GPY4", 2496 }, 2497 }, { 2498 .chip = { 2499 .base = EXYNOS5_GPY5(0), 2500 .ngpio = EXYNOS5_GPIO_Y5_NR, 2501 .label = "GPY5", 2502 }, 2503 }, { 2504 .chip = { 2505 .base = EXYNOS5_GPY6(0), 2506 .ngpio = EXYNOS5_GPIO_Y6_NR, 2507 .label = "GPY6", 2508 }, 2509 }, { 2510 .config = &samsung_gpio_cfgs[9], 2511 .irq_base = IRQ_EINT(0), 2512 .chip = { 2513 .base = EXYNOS5_GPX0(0), 2514 .ngpio = EXYNOS5_GPIO_X0_NR, 2515 .label = "GPX0", 2516 .to_irq = samsung_gpiolib_to_irq, 2517 }, 2518 }, { 2519 .config = &samsung_gpio_cfgs[9], 2520 .irq_base = IRQ_EINT(8), 2521 .chip = { 2522 .base = EXYNOS5_GPX1(0), 2523 .ngpio = EXYNOS5_GPIO_X1_NR, 2524 .label = "GPX1", 2525 .to_irq = samsung_gpiolib_to_irq, 2526 }, 2527 }, { 2528 .config = &samsung_gpio_cfgs[9], 2529 .irq_base = IRQ_EINT(16), 2530 .chip = { 2531 .base = EXYNOS5_GPX2(0), 2532 .ngpio = EXYNOS5_GPIO_X2_NR, 2533 .label = "GPX2", 2534 .to_irq = samsung_gpiolib_to_irq, 2535 }, 2536 }, { 2537 .config = &samsung_gpio_cfgs[9], 2538 .irq_base = IRQ_EINT(24), 2539 .chip = { 2540 .base = EXYNOS5_GPX3(0), 2541 .ngpio = EXYNOS5_GPIO_X3_NR, 2542 .label = "GPX3", 2543 .to_irq = samsung_gpiolib_to_irq, 2544 }, 2545 }, 2546}; 2547#endif 2548 2549#ifdef CONFIG_ARCH_EXYNOS5 2550static struct samsung_gpio_chip exynos5_gpios_2[] = { 2551 { 2552 .chip = { 2553 .base = EXYNOS5_GPE0(0), 2554 .ngpio = EXYNOS5_GPIO_E0_NR, 2555 .label = "GPE0", 2556 }, 2557 }, { 2558 .chip = { 2559 .base = EXYNOS5_GPE1(0), 2560 .ngpio = EXYNOS5_GPIO_E1_NR, 2561 .label = "GPE1", 2562 }, 2563 }, { 2564 .chip = { 2565 .base = EXYNOS5_GPF0(0), 2566 .ngpio = EXYNOS5_GPIO_F0_NR, 2567 .label = "GPF0", 2568 }, 2569 }, { 2570 .chip = { 2571 .base = EXYNOS5_GPF1(0), 2572 .ngpio = EXYNOS5_GPIO_F1_NR, 2573 .label = "GPF1", 2574 }, 2575 }, { 2576 .chip = { 2577 .base = EXYNOS5_GPG0(0), 2578 .ngpio = EXYNOS5_GPIO_G0_NR, 2579 .label = "GPG0", 2580 }, 2581 }, { 2582 .chip = { 2583 .base = EXYNOS5_GPG1(0), 2584 .ngpio = EXYNOS5_GPIO_G1_NR, 2585 .label = "GPG1", 2586 }, 2587 }, { 2588 .chip = { 2589 .base = EXYNOS5_GPG2(0), 2590 .ngpio = EXYNOS5_GPIO_G2_NR, 2591 .label = "GPG2", 2592 }, 2593 }, { 2594 .chip = { 2595 .base = EXYNOS5_GPH0(0), 2596 .ngpio = EXYNOS5_GPIO_H0_NR, 2597 .label = "GPH0", 2598 }, 2599 }, { 2600 .chip = { 2601 .base = EXYNOS5_GPH1(0), 2602 .ngpio = EXYNOS5_GPIO_H1_NR, 2603 .label = "GPH1", 2604 2605 }, 2606 }, 2607}; 2608#endif 2609 2610#ifdef CONFIG_ARCH_EXYNOS5 2611static struct samsung_gpio_chip exynos5_gpios_3[] = { 2612 { 2613 .chip = { 2614 .base = EXYNOS5_GPV0(0), 2615 .ngpio = EXYNOS5_GPIO_V0_NR, 2616 .label = "GPV0", 2617 }, 2618 }, { 2619 .chip = { 2620 .base = EXYNOS5_GPV1(0), 2621 .ngpio = EXYNOS5_GPIO_V1_NR, 2622 .label = "GPV1", 2623 }, 2624 }, { 2625 .chip = { 2626 .base = EXYNOS5_GPV2(0), 2627 .ngpio = EXYNOS5_GPIO_V2_NR, 2628 .label = "GPV2", 2629 }, 2630 }, { 2631 .chip = { 2632 .base = EXYNOS5_GPV3(0), 2633 .ngpio = EXYNOS5_GPIO_V3_NR, 2634 .label = "GPV3", 2635 }, 2636 }, { 2637 .chip = { 2638 .base = EXYNOS5_GPV4(0), 2639 .ngpio = EXYNOS5_GPIO_V4_NR, 2640 .label = "GPV4", 2641 }, 2642 }, 2643}; 2644#endif 2645 2646#ifdef CONFIG_ARCH_EXYNOS5 2647static struct samsung_gpio_chip exynos5_gpios_4[] = { 2648 { 2649 .chip = { 2650 .base = EXYNOS5_GPZ(0), 2651 .ngpio = EXYNOS5_GPIO_Z_NR, 2652 .label = "GPZ", 2653 }, 2654 }, 2655}; 2656#endif 2657 2658 2659#if defined(CONFIG_ARCH_EXYNOS) && defined(CONFIG_OF) 2660static int exynos_gpio_xlate(struct gpio_chip *gc, 2661 const struct of_phandle_args *gpiospec, u32 *flags) 2662{ 2663 unsigned int pin; 2664 2665 if (WARN_ON(gc->of_gpio_n_cells < 4)) 2666 return -EINVAL; 2667 2668 if (WARN_ON(gpiospec->args_count < gc->of_gpio_n_cells)) 2669 return -EINVAL; 2670 2671 if (gpiospec->args[0] > gc->ngpio) 2672 return -EINVAL; 2673 2674 pin = gc->base + gpiospec->args[0]; 2675 2676 if (s3c_gpio_cfgpin(pin, S3C_GPIO_SFN(gpiospec->args[1]))) 2677 pr_warn("gpio_xlate: failed to set pin function\n"); 2678 if (s3c_gpio_setpull(pin, gpiospec->args[2])) 2679 pr_warn("gpio_xlate: failed to set pin pull up/down\n"); 2680 if (s5p_gpio_set_drvstr(pin, gpiospec->args[3])) 2681 pr_warn("gpio_xlate: failed to set pin drive strength\n"); 2682 2683 return gpiospec->args[0]; 2684} 2685 2686static const struct of_device_id exynos_gpio_dt_match[] __initdata = { 2687 { .compatible = "samsung,exynos4-gpio", }, 2688 {} 2689}; 2690 2691static __init void exynos_gpiolib_attach_ofnode(struct samsung_gpio_chip *chip, 2692 u64 base, u64 offset) 2693{ 2694 struct gpio_chip *gc = &chip->chip; 2695 u64 address; 2696 2697 if (!of_have_populated_dt()) 2698 return; 2699 2700 address = chip->base ? base + ((u32)chip->base & 0xfff) : base + offset; 2701 gc->of_node = of_find_matching_node_by_address(NULL, 2702 exynos_gpio_dt_match, address); 2703 if (!gc->of_node) { 2704 pr_info("gpio: device tree node not found for gpio controller" 2705 " with base address %08llx\n", address); 2706 return; 2707 } 2708 gc->of_gpio_n_cells = 4; 2709 gc->of_xlate = exynos_gpio_xlate; 2710} 2711#elif defined(CONFIG_ARCH_EXYNOS) 2712static __init void exynos_gpiolib_attach_ofnode(struct samsung_gpio_chip *chip, 2713 u64 base, u64 offset) 2714{ 2715 return; 2716} 2717#endif /* defined(CONFIG_ARCH_EXYNOS) && defined(CONFIG_OF) */ 2718 2719/* TODO: cleanup soc_is_* */ 2720static __init int samsung_gpiolib_init(void) 2721{ 2722 struct samsung_gpio_chip *chip; 2723 int i, nr_chips; 2724#if defined(CONFIG_CPU_EXYNOS4210) || defined(CONFIG_SOC_EXYNOS5250) 2725 void __iomem *gpio_base1, *gpio_base2, *gpio_base3, *gpio_base4; 2726#endif 2727 int group = 0; 2728 2729 samsung_gpiolib_set_cfg(samsung_gpio_cfgs, ARRAY_SIZE(samsung_gpio_cfgs)); 2730 2731 if (soc_is_s3c24xx()) { 2732 s3c24xx_gpiolib_add_chips(s3c24xx_gpios, 2733 ARRAY_SIZE(s3c24xx_gpios), S3C24XX_VA_GPIO); 2734 } else if (soc_is_s3c64xx()) { 2735 samsung_gpiolib_add_2bit_chips(s3c64xx_gpios_2bit, 2736 ARRAY_SIZE(s3c64xx_gpios_2bit), 2737 S3C64XX_VA_GPIO + 0xE0, 0x20); 2738 samsung_gpiolib_add_4bit_chips(s3c64xx_gpios_4bit, 2739 ARRAY_SIZE(s3c64xx_gpios_4bit), 2740 S3C64XX_VA_GPIO); 2741 samsung_gpiolib_add_4bit2_chips(s3c64xx_gpios_4bit2, 2742 ARRAY_SIZE(s3c64xx_gpios_4bit2)); 2743 } else if (soc_is_s5p6440()) { 2744 samsung_gpiolib_add_2bit_chips(s5p6440_gpios_2bit, 2745 ARRAY_SIZE(s5p6440_gpios_2bit), NULL, 0x0); 2746 samsung_gpiolib_add_4bit_chips(s5p6440_gpios_4bit, 2747 ARRAY_SIZE(s5p6440_gpios_4bit), S5P_VA_GPIO); 2748 samsung_gpiolib_add_4bit2_chips(s5p6440_gpios_4bit2, 2749 ARRAY_SIZE(s5p6440_gpios_4bit2)); 2750 s5p64x0_gpiolib_add_rbank(s5p6440_gpios_rbank, 2751 ARRAY_SIZE(s5p6440_gpios_rbank)); 2752 } else if (soc_is_s5p6450()) { 2753 samsung_gpiolib_add_2bit_chips(s5p6450_gpios_2bit, 2754 ARRAY_SIZE(s5p6450_gpios_2bit), NULL, 0x0); 2755 samsung_gpiolib_add_4bit_chips(s5p6450_gpios_4bit, 2756 ARRAY_SIZE(s5p6450_gpios_4bit), S5P_VA_GPIO); 2757 samsung_gpiolib_add_4bit2_chips(s5p6450_gpios_4bit2, 2758 ARRAY_SIZE(s5p6450_gpios_4bit2)); 2759 s5p64x0_gpiolib_add_rbank(s5p6450_gpios_rbank, 2760 ARRAY_SIZE(s5p6450_gpios_rbank)); 2761 } else if (soc_is_s5pc100()) { 2762 group = 0; 2763 chip = s5pc100_gpios_4bit; 2764 nr_chips = ARRAY_SIZE(s5pc100_gpios_4bit); 2765 2766 for (i = 0; i < nr_chips; i++, chip++) { 2767 if (!chip->config) { 2768 chip->config = &samsung_gpio_cfgs[3]; 2769 chip->group = group++; 2770 } 2771 } 2772 samsung_gpiolib_add_4bit_chips(s5pc100_gpios_4bit, nr_chips, S5P_VA_GPIO); 2773#if defined(CONFIG_CPU_S5PC100) && defined(CONFIG_S5P_GPIO_INT) 2774 s5p_register_gpioint_bank(IRQ_GPIOINT, 0, S5P_GPIOINT_GROUP_MAXNR); 2775#endif 2776 } else if (soc_is_s5pv210()) { 2777 group = 0; 2778 chip = s5pv210_gpios_4bit; 2779 nr_chips = ARRAY_SIZE(s5pv210_gpios_4bit); 2780 2781 for (i = 0; i < nr_chips; i++, chip++) { 2782 if (!chip->config) { 2783 chip->config = &samsung_gpio_cfgs[3]; 2784 chip->group = group++; 2785 } 2786 } 2787 samsung_gpiolib_add_4bit_chips(s5pv210_gpios_4bit, nr_chips, S5P_VA_GPIO); 2788#if defined(CONFIG_CPU_S5PV210) && defined(CONFIG_S5P_GPIO_INT) 2789 s5p_register_gpioint_bank(IRQ_GPIOINT, 0, S5P_GPIOINT_GROUP_MAXNR); 2790#endif 2791 } else if (soc_is_exynos4210()) { 2792#ifdef CONFIG_CPU_EXYNOS4210 2793 void __iomem *gpx_base; 2794 2795 /* gpio part1 */ 2796 gpio_base1 = ioremap(EXYNOS4_PA_GPIO1, SZ_4K); 2797 if (gpio_base1 == NULL) { 2798 pr_err("unable to ioremap for gpio_base1\n"); 2799 goto err_ioremap1; 2800 } 2801 2802 chip = exynos4_gpios_1; 2803 nr_chips = ARRAY_SIZE(exynos4_gpios_1); 2804 2805 for (i = 0; i < nr_chips; i++, chip++) { 2806 if (!chip->config) { 2807 chip->config = &exynos_gpio_cfg; 2808 chip->group = group++; 2809 } 2810 exynos_gpiolib_attach_ofnode(chip, 2811 EXYNOS4_PA_GPIO1, i * 0x20); 2812 } 2813 samsung_gpiolib_add_4bit_chips(exynos4_gpios_1, 2814 nr_chips, gpio_base1); 2815 2816 /* gpio part2 */ 2817 gpio_base2 = ioremap(EXYNOS4_PA_GPIO2, SZ_4K); 2818 if (gpio_base2 == NULL) { 2819 pr_err("unable to ioremap for gpio_base2\n"); 2820 goto err_ioremap2; 2821 } 2822 2823 /* need to set base address for gpx */ 2824 chip = &exynos4_gpios_2[16]; 2825 gpx_base = gpio_base2 + 0xC00; 2826 for (i = 0; i < 4; i++, chip++, gpx_base += 0x20) 2827 chip->base = gpx_base; 2828 2829 chip = exynos4_gpios_2; 2830 nr_chips = ARRAY_SIZE(exynos4_gpios_2); 2831 2832 for (i = 0; i < nr_chips; i++, chip++) { 2833 if (!chip->config) { 2834 chip->config = &exynos_gpio_cfg; 2835 chip->group = group++; 2836 } 2837 exynos_gpiolib_attach_ofnode(chip, 2838 EXYNOS4_PA_GPIO2, i * 0x20); 2839 } 2840 samsung_gpiolib_add_4bit_chips(exynos4_gpios_2, 2841 nr_chips, gpio_base2); 2842 2843 /* gpio part3 */ 2844 gpio_base3 = ioremap(EXYNOS4_PA_GPIO3, SZ_256); 2845 if (gpio_base3 == NULL) { 2846 pr_err("unable to ioremap for gpio_base3\n"); 2847 goto err_ioremap3; 2848 } 2849 2850 chip = exynos4_gpios_3; 2851 nr_chips = ARRAY_SIZE(exynos4_gpios_3); 2852 2853 for (i = 0; i < nr_chips; i++, chip++) { 2854 if (!chip->config) { 2855 chip->config = &exynos_gpio_cfg; 2856 chip->group = group++; 2857 } 2858 exynos_gpiolib_attach_ofnode(chip, 2859 EXYNOS4_PA_GPIO3, i * 0x20); 2860 } 2861 samsung_gpiolib_add_4bit_chips(exynos4_gpios_3, 2862 nr_chips, gpio_base3); 2863 2864#if defined(CONFIG_CPU_EXYNOS4210) && defined(CONFIG_S5P_GPIO_INT) 2865 s5p_register_gpioint_bank(IRQ_GPIO_XA, 0, IRQ_GPIO1_NR_GROUPS); 2866 s5p_register_gpioint_bank(IRQ_GPIO_XB, IRQ_GPIO1_NR_GROUPS, IRQ_GPIO2_NR_GROUPS); 2867#endif 2868 2869#endif /* CONFIG_CPU_EXYNOS4210 */ 2870 } else if (soc_is_exynos5250()) { 2871#ifdef CONFIG_SOC_EXYNOS5250 2872 void __iomem *gpx_base; 2873 2874 /* gpio part1 */ 2875 gpio_base1 = ioremap(EXYNOS5_PA_GPIO1, SZ_4K); 2876 if (gpio_base1 == NULL) { 2877 pr_err("unable to ioremap for gpio_base1\n"); 2878 goto err_ioremap1; 2879 } 2880 2881 /* need to set base address for gpx */ 2882 chip = &exynos5_gpios_1[20]; 2883 gpx_base = gpio_base1 + 0xC00; 2884 for (i = 0; i < 4; i++, chip++, gpx_base += 0x20) 2885 chip->base = gpx_base; 2886 2887 chip = exynos5_gpios_1; 2888 nr_chips = ARRAY_SIZE(exynos5_gpios_1); 2889 2890 for (i = 0; i < nr_chips; i++, chip++) { 2891 if (!chip->config) { 2892 chip->config = &exynos_gpio_cfg; 2893 chip->group = group++; 2894 } 2895 exynos_gpiolib_attach_ofnode(chip, 2896 EXYNOS5_PA_GPIO1, i * 0x20); 2897 } 2898 samsung_gpiolib_add_4bit_chips(exynos5_gpios_1, 2899 nr_chips, gpio_base1); 2900 2901 /* gpio part2 */ 2902 gpio_base2 = ioremap(EXYNOS5_PA_GPIO2, SZ_4K); 2903 if (gpio_base2 == NULL) { 2904 pr_err("unable to ioremap for gpio_base2\n"); 2905 goto err_ioremap2; 2906 } 2907 2908 chip = exynos5_gpios_2; 2909 nr_chips = ARRAY_SIZE(exynos5_gpios_2); 2910 2911 for (i = 0; i < nr_chips; i++, chip++) { 2912 if (!chip->config) { 2913 chip->config = &exynos_gpio_cfg; 2914 chip->group = group++; 2915 } 2916 exynos_gpiolib_attach_ofnode(chip, 2917 EXYNOS5_PA_GPIO2, i * 0x20); 2918 } 2919 samsung_gpiolib_add_4bit_chips(exynos5_gpios_2, 2920 nr_chips, gpio_base2); 2921 2922 /* gpio part3 */ 2923 gpio_base3 = ioremap(EXYNOS5_PA_GPIO3, SZ_4K); 2924 if (gpio_base3 == NULL) { 2925 pr_err("unable to ioremap for gpio_base3\n"); 2926 goto err_ioremap3; 2927 } 2928 2929 /* need to set base address for gpv */ 2930 exynos5_gpios_3[0].base = gpio_base3; 2931 exynos5_gpios_3[1].base = gpio_base3 + 0x20; 2932 exynos5_gpios_3[2].base = gpio_base3 + 0x60; 2933 exynos5_gpios_3[3].base = gpio_base3 + 0x80; 2934 exynos5_gpios_3[4].base = gpio_base3 + 0xC0; 2935 2936 chip = exynos5_gpios_3; 2937 nr_chips = ARRAY_SIZE(exynos5_gpios_3); 2938 2939 for (i = 0; i < nr_chips; i++, chip++) { 2940 if (!chip->config) { 2941 chip->config = &exynos_gpio_cfg; 2942 chip->group = group++; 2943 } 2944 exynos_gpiolib_attach_ofnode(chip, 2945 EXYNOS5_PA_GPIO3, i * 0x20); 2946 } 2947 samsung_gpiolib_add_4bit_chips(exynos5_gpios_3, 2948 nr_chips, gpio_base3); 2949 2950 /* gpio part4 */ 2951 gpio_base4 = ioremap(EXYNOS5_PA_GPIO4, SZ_4K); 2952 if (gpio_base4 == NULL) { 2953 pr_err("unable to ioremap for gpio_base4\n"); 2954 goto err_ioremap4; 2955 } 2956 2957 chip = exynos5_gpios_4; 2958 nr_chips = ARRAY_SIZE(exynos5_gpios_4); 2959 2960 for (i = 0; i < nr_chips; i++, chip++) { 2961 if (!chip->config) { 2962 chip->config = &exynos_gpio_cfg; 2963 chip->group = group++; 2964 } 2965 exynos_gpiolib_attach_ofnode(chip, 2966 EXYNOS5_PA_GPIO4, i * 0x20); 2967 } 2968 samsung_gpiolib_add_4bit_chips(exynos5_gpios_4, 2969 nr_chips, gpio_base4); 2970#endif /* CONFIG_SOC_EXYNOS5250 */ 2971 } else { 2972 WARN(1, "Unknown SoC in gpio-samsung, no GPIOs added\n"); 2973 return -ENODEV; 2974 } 2975 2976 return 0; 2977 2978#if defined(CONFIG_CPU_EXYNOS4210) || defined(CONFIG_SOC_EXYNOS5250) 2979err_ioremap4: 2980 iounmap(gpio_base3); 2981err_ioremap3: 2982 iounmap(gpio_base2); 2983err_ioremap2: 2984 iounmap(gpio_base1); 2985err_ioremap1: 2986 return -ENOMEM; 2987#endif 2988} 2989core_initcall(samsung_gpiolib_init); 2990 2991int s3c_gpio_cfgpin(unsigned int pin, unsigned int config) 2992{ 2993 struct samsung_gpio_chip *chip = samsung_gpiolib_getchip(pin); 2994 unsigned long flags; 2995 int offset; 2996 int ret; 2997 2998 if (!chip) 2999 return -EINVAL; 3000 3001 offset = pin - chip->chip.base; 3002 3003 samsung_gpio_lock(chip, flags); 3004 ret = samsung_gpio_do_setcfg(chip, offset, config); 3005 samsung_gpio_unlock(chip, flags); 3006 3007 return ret; 3008} 3009EXPORT_SYMBOL(s3c_gpio_cfgpin); 3010 3011int s3c_gpio_cfgpin_range(unsigned int start, unsigned int nr, 3012 unsigned int cfg) 3013{ 3014 int ret; 3015 3016 for (; nr > 0; nr--, start++) { 3017 ret = s3c_gpio_cfgpin(start, cfg); 3018 if (ret != 0) 3019 return ret; 3020 } 3021 3022 return 0; 3023} 3024EXPORT_SYMBOL_GPL(s3c_gpio_cfgpin_range); 3025 3026int s3c_gpio_cfgall_range(unsigned int start, unsigned int nr, 3027 unsigned int cfg, samsung_gpio_pull_t pull) 3028{ 3029 int ret; 3030 3031 for (; nr > 0; nr--, start++) { 3032 s3c_gpio_setpull(start, pull); 3033 ret = s3c_gpio_cfgpin(start, cfg); 3034 if (ret != 0) 3035 return ret; 3036 } 3037 3038 return 0; 3039} 3040EXPORT_SYMBOL_GPL(s3c_gpio_cfgall_range); 3041 3042unsigned s3c_gpio_getcfg(unsigned int pin) 3043{ 3044 struct samsung_gpio_chip *chip = samsung_gpiolib_getchip(pin); 3045 unsigned long flags; 3046 unsigned ret = 0; 3047 int offset; 3048 3049 if (chip) { 3050 offset = pin - chip->chip.base; 3051 3052 samsung_gpio_lock(chip, flags); 3053 ret = samsung_gpio_do_getcfg(chip, offset); 3054 samsung_gpio_unlock(chip, flags); 3055 } 3056 3057 return ret; 3058} 3059EXPORT_SYMBOL(s3c_gpio_getcfg); 3060 3061int s3c_gpio_setpull(unsigned int pin, samsung_gpio_pull_t pull) 3062{ 3063 struct samsung_gpio_chip *chip = samsung_gpiolib_getchip(pin); 3064 unsigned long flags; 3065 int offset, ret; 3066 3067 if (!chip) 3068 return -EINVAL; 3069 3070 offset = pin - chip->chip.base; 3071 3072 samsung_gpio_lock(chip, flags); 3073 ret = samsung_gpio_do_setpull(chip, offset, pull); 3074 samsung_gpio_unlock(chip, flags); 3075 3076 return ret; 3077} 3078EXPORT_SYMBOL(s3c_gpio_setpull); 3079 3080samsung_gpio_pull_t s3c_gpio_getpull(unsigned int pin) 3081{ 3082 struct samsung_gpio_chip *chip = samsung_gpiolib_getchip(pin); 3083 unsigned long flags; 3084 int offset; 3085 u32 pup = 0; 3086 3087 if (chip) { 3088 offset = pin - chip->chip.base; 3089 3090 samsung_gpio_lock(chip, flags); 3091 pup = samsung_gpio_do_getpull(chip, offset); 3092 samsung_gpio_unlock(chip, flags); 3093 } 3094 3095 return (__force samsung_gpio_pull_t)pup; 3096} 3097EXPORT_SYMBOL(s3c_gpio_getpull); 3098 3099/* gpiolib wrappers until these are totally eliminated */ 3100 3101void s3c2410_gpio_pullup(unsigned int pin, unsigned int to) 3102{ 3103 int ret; 3104 3105 WARN_ON(to); /* should be none of these left */ 3106 3107 if (!to) { 3108 /* if pull is enabled, try first with up, and if that 3109 * fails, try using down */ 3110 3111 ret = s3c_gpio_setpull(pin, S3C_GPIO_PULL_UP); 3112 if (ret) 3113 s3c_gpio_setpull(pin, S3C_GPIO_PULL_DOWN); 3114 } else { 3115 s3c_gpio_setpull(pin, S3C_GPIO_PULL_NONE); 3116 } 3117} 3118EXPORT_SYMBOL(s3c2410_gpio_pullup); 3119 3120void s3c2410_gpio_setpin(unsigned int pin, unsigned int to) 3121{ 3122 /* do this via gpiolib until all users removed */ 3123 3124 gpio_request(pin, "temporary"); 3125 gpio_set_value(pin, to); 3126 gpio_free(pin); 3127} 3128EXPORT_SYMBOL(s3c2410_gpio_setpin); 3129 3130unsigned int s3c2410_gpio_getpin(unsigned int pin) 3131{ 3132 struct samsung_gpio_chip *chip = samsung_gpiolib_getchip(pin); 3133 unsigned long offs = pin - chip->chip.base; 3134 3135 return __raw_readl(chip->base + 0x04) & (1 << offs); 3136} 3137EXPORT_SYMBOL(s3c2410_gpio_getpin); 3138 3139#ifdef CONFIG_S5P_GPIO_DRVSTR 3140s5p_gpio_drvstr_t s5p_gpio_get_drvstr(unsigned int pin) 3141{ 3142 struct samsung_gpio_chip *chip = samsung_gpiolib_getchip(pin); 3143 unsigned int off; 3144 void __iomem *reg; 3145 int shift; 3146 u32 drvstr; 3147 3148 if (!chip) 3149 return -EINVAL; 3150 3151 off = pin - chip->chip.base; 3152 shift = off * 2; 3153 reg = chip->base + 0x0C; 3154 3155 drvstr = __raw_readl(reg); 3156 drvstr = drvstr >> shift; 3157 drvstr &= 0x3; 3158 3159 return (__force s5p_gpio_drvstr_t)drvstr; 3160} 3161EXPORT_SYMBOL(s5p_gpio_get_drvstr); 3162 3163int s5p_gpio_set_drvstr(unsigned int pin, s5p_gpio_drvstr_t drvstr) 3164{ 3165 struct samsung_gpio_chip *chip = samsung_gpiolib_getchip(pin); 3166 unsigned int off; 3167 void __iomem *reg; 3168 int shift; 3169 u32 tmp; 3170 3171 if (!chip) 3172 return -EINVAL; 3173 3174 off = pin - chip->chip.base; 3175 shift = off * 2; 3176 reg = chip->base + 0x0C; 3177 3178 tmp = __raw_readl(reg); 3179 tmp &= ~(0x3 << shift); 3180 tmp |= drvstr << shift; 3181 3182 __raw_writel(tmp, reg); 3183 3184 return 0; 3185} 3186EXPORT_SYMBOL(s5p_gpio_set_drvstr); 3187#endif /* CONFIG_S5P_GPIO_DRVSTR */ 3188 3189#ifdef CONFIG_PLAT_S3C24XX 3190unsigned int s3c2410_modify_misccr(unsigned int clear, unsigned int change) 3191{ 3192 unsigned long flags; 3193 unsigned long misccr; 3194 3195 local_irq_save(flags); 3196 misccr = __raw_readl(S3C24XX_MISCCR); 3197 misccr &= ~clear; 3198 misccr ^= change; 3199 __raw_writel(misccr, S3C24XX_MISCCR); 3200 local_irq_restore(flags); 3201 3202 return misccr; 3203} 3204EXPORT_SYMBOL(s3c2410_modify_misccr); 3205#endif 3206