gpio.c 5.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244
  1. /*
  2. * Atheros AR71XX/AR724X/AR913X GPIO API support
  3. *
  4. * Copyright (C) 2010-2011 Jaiganesh Narayanan <jnarayanan@atheros.com>
  5. * Copyright (C) 2008-2011 Gabor Juhos <juhosg@openwrt.org>
  6. * Copyright (C) 2008 Imre Kaloz <kaloz@openwrt.org>
  7. *
  8. * Parts of this file are based on Atheros' 2.6.15/2.6.31 BSP
  9. *
  10. * This program is free software; you can redistribute it and/or modify it
  11. * under the terms of the GNU General Public License version 2 as published
  12. * by the Free Software Foundation.
  13. */
  14. #include <linux/kernel.h>
  15. #include <linux/init.h>
  16. #include <linux/module.h>
  17. #include <linux/types.h>
  18. #include <linux/spinlock.h>
  19. #include <linux/io.h>
  20. #include <linux/ioport.h>
  21. #include <linux/gpio.h>
  22. #include <asm/mach-ath79/ar71xx_regs.h>
  23. #include <asm/mach-ath79/ath79.h>
  24. #include "common.h"
  25. static void __iomem *ath79_gpio_base;
  26. static unsigned long ath79_gpio_count;
  27. static DEFINE_SPINLOCK(ath79_gpio_lock);
  28. static void __ath79_gpio_set_value(unsigned gpio, int value)
  29. {
  30. void __iomem *base = ath79_gpio_base;
  31. if (value)
  32. __raw_writel(1 << gpio, base + AR71XX_GPIO_REG_SET);
  33. else
  34. __raw_writel(1 << gpio, base + AR71XX_GPIO_REG_CLEAR);
  35. }
  36. static int __ath79_gpio_get_value(unsigned gpio)
  37. {
  38. return (__raw_readl(ath79_gpio_base + AR71XX_GPIO_REG_IN) >> gpio) & 1;
  39. }
  40. static int ath79_gpio_get_value(struct gpio_chip *chip, unsigned offset)
  41. {
  42. return __ath79_gpio_get_value(offset);
  43. }
  44. static void ath79_gpio_set_value(struct gpio_chip *chip,
  45. unsigned offset, int value)
  46. {
  47. __ath79_gpio_set_value(offset, value);
  48. }
  49. static int ath79_gpio_direction_input(struct gpio_chip *chip,
  50. unsigned offset)
  51. {
  52. void __iomem *base = ath79_gpio_base;
  53. unsigned long flags;
  54. spin_lock_irqsave(&ath79_gpio_lock, flags);
  55. __raw_writel(__raw_readl(base + AR71XX_GPIO_REG_OE) & ~(1 << offset),
  56. base + AR71XX_GPIO_REG_OE);
  57. spin_unlock_irqrestore(&ath79_gpio_lock, flags);
  58. return 0;
  59. }
  60. static int ath79_gpio_direction_output(struct gpio_chip *chip,
  61. unsigned offset, int value)
  62. {
  63. void __iomem *base = ath79_gpio_base;
  64. unsigned long flags;
  65. spin_lock_irqsave(&ath79_gpio_lock, flags);
  66. if (value)
  67. __raw_writel(1 << offset, base + AR71XX_GPIO_REG_SET);
  68. else
  69. __raw_writel(1 << offset, base + AR71XX_GPIO_REG_CLEAR);
  70. __raw_writel(__raw_readl(base + AR71XX_GPIO_REG_OE) | (1 << offset),
  71. base + AR71XX_GPIO_REG_OE);
  72. spin_unlock_irqrestore(&ath79_gpio_lock, flags);
  73. return 0;
  74. }
  75. static int ar934x_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
  76. {
  77. void __iomem *base = ath79_gpio_base;
  78. unsigned long flags;
  79. spin_lock_irqsave(&ath79_gpio_lock, flags);
  80. __raw_writel(__raw_readl(base + AR71XX_GPIO_REG_OE) | (1 << offset),
  81. base + AR71XX_GPIO_REG_OE);
  82. spin_unlock_irqrestore(&ath79_gpio_lock, flags);
  83. return 0;
  84. }
  85. static int ar934x_gpio_direction_output(struct gpio_chip *chip, unsigned offset,
  86. int value)
  87. {
  88. void __iomem *base = ath79_gpio_base;
  89. unsigned long flags;
  90. spin_lock_irqsave(&ath79_gpio_lock, flags);
  91. if (value)
  92. __raw_writel(1 << offset, base + AR71XX_GPIO_REG_SET);
  93. else
  94. __raw_writel(1 << offset, base + AR71XX_GPIO_REG_CLEAR);
  95. __raw_writel(__raw_readl(base + AR71XX_GPIO_REG_OE) & ~(1 << offset),
  96. base + AR71XX_GPIO_REG_OE);
  97. spin_unlock_irqrestore(&ath79_gpio_lock, flags);
  98. return 0;
  99. }
  100. static struct gpio_chip ath79_gpio_chip = {
  101. .label = "ath79",
  102. .get = ath79_gpio_get_value,
  103. .set = ath79_gpio_set_value,
  104. .direction_input = ath79_gpio_direction_input,
  105. .direction_output = ath79_gpio_direction_output,
  106. .base = 0,
  107. };
  108. void ath79_gpio_function_enable(u32 mask)
  109. {
  110. void __iomem *base = ath79_gpio_base;
  111. unsigned long flags;
  112. spin_lock_irqsave(&ath79_gpio_lock, flags);
  113. __raw_writel(__raw_readl(base + AR71XX_GPIO_REG_FUNC) | mask,
  114. base + AR71XX_GPIO_REG_FUNC);
  115. /* flush write */
  116. __raw_readl(base + AR71XX_GPIO_REG_FUNC);
  117. spin_unlock_irqrestore(&ath79_gpio_lock, flags);
  118. }
  119. void ath79_gpio_function_disable(u32 mask)
  120. {
  121. void __iomem *base = ath79_gpio_base;
  122. unsigned long flags;
  123. spin_lock_irqsave(&ath79_gpio_lock, flags);
  124. __raw_writel(__raw_readl(base + AR71XX_GPIO_REG_FUNC) & ~mask,
  125. base + AR71XX_GPIO_REG_FUNC);
  126. /* flush write */
  127. __raw_readl(base + AR71XX_GPIO_REG_FUNC);
  128. spin_unlock_irqrestore(&ath79_gpio_lock, flags);
  129. }
  130. void ath79_gpio_function_setup(u32 set, u32 clear)
  131. {
  132. void __iomem *base = ath79_gpio_base;
  133. unsigned long flags;
  134. spin_lock_irqsave(&ath79_gpio_lock, flags);
  135. __raw_writel((__raw_readl(base + AR71XX_GPIO_REG_FUNC) & ~clear) | set,
  136. base + AR71XX_GPIO_REG_FUNC);
  137. /* flush write */
  138. __raw_readl(base + AR71XX_GPIO_REG_FUNC);
  139. spin_unlock_irqrestore(&ath79_gpio_lock, flags);
  140. }
  141. void __init ath79_gpio_init(void)
  142. {
  143. int err;
  144. if (soc_is_ar71xx())
  145. ath79_gpio_count = AR71XX_GPIO_COUNT;
  146. else if (soc_is_ar724x())
  147. ath79_gpio_count = AR724X_GPIO_COUNT;
  148. else if (soc_is_ar913x())
  149. ath79_gpio_count = AR913X_GPIO_COUNT;
  150. else if (soc_is_ar933x())
  151. ath79_gpio_count = AR933X_GPIO_COUNT;
  152. else if (soc_is_ar934x())
  153. ath79_gpio_count = AR934X_GPIO_COUNT;
  154. else
  155. BUG();
  156. ath79_gpio_base = ioremap_nocache(AR71XX_GPIO_BASE, AR71XX_GPIO_SIZE);
  157. ath79_gpio_chip.ngpio = ath79_gpio_count;
  158. if (soc_is_ar934x()) {
  159. ath79_gpio_chip.direction_input = ar934x_gpio_direction_input;
  160. ath79_gpio_chip.direction_output = ar934x_gpio_direction_output;
  161. }
  162. err = gpiochip_add(&ath79_gpio_chip);
  163. if (err)
  164. panic("cannot add AR71xx GPIO chip, error=%d", err);
  165. }
  166. int gpio_get_value(unsigned gpio)
  167. {
  168. if (gpio < ath79_gpio_count)
  169. return __ath79_gpio_get_value(gpio);
  170. return __gpio_get_value(gpio);
  171. }
  172. EXPORT_SYMBOL(gpio_get_value);
  173. void gpio_set_value(unsigned gpio, int value)
  174. {
  175. if (gpio < ath79_gpio_count)
  176. __ath79_gpio_set_value(gpio, value);
  177. else
  178. __gpio_set_value(gpio, value);
  179. }
  180. EXPORT_SYMBOL(gpio_set_value);
  181. int gpio_to_irq(unsigned gpio)
  182. {
  183. /* FIXME */
  184. return -EINVAL;
  185. }
  186. EXPORT_SYMBOL(gpio_to_irq);
  187. int irq_to_gpio(unsigned irq)
  188. {
  189. /* FIXME */
  190. return -EINVAL;
  191. }
  192. EXPORT_SYMBOL(irq_to_gpio);