gpio.c 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231
  1. /*
  2. * s6000 gpio driver
  3. *
  4. * Copyright (c) 2009 emlix GmbH
  5. * Authors: Oskar Schirmer <os@emlix.com>
  6. * Johannes Weiner <jw@emlix.com>
  7. * Daniel Gloeckner <dg@emlix.com>
  8. */
  9. #include <linux/bitops.h>
  10. #include <linux/kernel.h>
  11. #include <linux/module.h>
  12. #include <linux/init.h>
  13. #include <linux/io.h>
  14. #include <linux/irq.h>
  15. #include <linux/gpio.h>
  16. #include <variant/hardware.h>
  17. #define IRQ_BASE XTENSA_NR_IRQS
  18. #define S6_GPIO_DATA 0x000
  19. #define S6_GPIO_IS 0x404
  20. #define S6_GPIO_IBE 0x408
  21. #define S6_GPIO_IEV 0x40C
  22. #define S6_GPIO_IE 0x410
  23. #define S6_GPIO_RIS 0x414
  24. #define S6_GPIO_MIS 0x418
  25. #define S6_GPIO_IC 0x41C
  26. #define S6_GPIO_AFSEL 0x420
  27. #define S6_GPIO_DIR 0x800
  28. #define S6_GPIO_BANK(nr) ((nr) * 0x1000)
  29. #define S6_GPIO_MASK(nr) (4 << (nr))
  30. #define S6_GPIO_OFFSET(nr) \
  31. (S6_GPIO_BANK((nr) >> 3) + S6_GPIO_MASK((nr) & 7))
  32. static int direction_input(struct gpio_chip *chip, unsigned int off)
  33. {
  34. writeb(0, S6_REG_GPIO + S6_GPIO_DIR + S6_GPIO_OFFSET(off));
  35. return 0;
  36. }
  37. static int get(struct gpio_chip *chip, unsigned int off)
  38. {
  39. return readb(S6_REG_GPIO + S6_GPIO_DATA + S6_GPIO_OFFSET(off));
  40. }
  41. static int direction_output(struct gpio_chip *chip, unsigned int off, int val)
  42. {
  43. unsigned rel = S6_GPIO_OFFSET(off);
  44. writeb(~0, S6_REG_GPIO + S6_GPIO_DIR + rel);
  45. writeb(val ? ~0 : 0, S6_REG_GPIO + S6_GPIO_DATA + rel);
  46. return 0;
  47. }
  48. static void set(struct gpio_chip *chip, unsigned int off, int val)
  49. {
  50. writeb(val ? ~0 : 0, S6_REG_GPIO + S6_GPIO_DATA + S6_GPIO_OFFSET(off));
  51. }
  52. static int to_irq(struct gpio_chip *chip, unsigned offset)
  53. {
  54. if (offset < 8)
  55. return offset + IRQ_BASE;
  56. return -EINVAL;
  57. }
  58. static struct gpio_chip gpiochip = {
  59. .owner = THIS_MODULE,
  60. .direction_input = direction_input,
  61. .get = get,
  62. .direction_output = direction_output,
  63. .set = set,
  64. .to_irq = to_irq,
  65. .base = 0,
  66. .ngpio = 24,
  67. .can_sleep = 0, /* no blocking io needed */
  68. .exported = 0, /* no exporting to userspace */
  69. };
  70. int s6_gpio_init(u32 afsel)
  71. {
  72. writeb(afsel, S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_AFSEL);
  73. writeb(afsel >> 8, S6_REG_GPIO + S6_GPIO_BANK(1) + S6_GPIO_AFSEL);
  74. writeb(afsel >> 16, S6_REG_GPIO + S6_GPIO_BANK(2) + S6_GPIO_AFSEL);
  75. return gpiochip_add(&gpiochip);
  76. }
  77. static void ack(struct irq_data *d)
  78. {
  79. writeb(1 << (d->irq - IRQ_BASE), S6_REG_GPIO + S6_GPIO_IC);
  80. }
  81. static void mask(struct irq_data *d)
  82. {
  83. u8 r = readb(S6_REG_GPIO + S6_GPIO_IE);
  84. r &= ~(1 << (d->irq - IRQ_BASE));
  85. writeb(r, S6_REG_GPIO + S6_GPIO_IE);
  86. }
  87. static void unmask(struct irq_data *d)
  88. {
  89. u8 m = readb(S6_REG_GPIO + S6_GPIO_IE);
  90. m |= 1 << (d->irq - IRQ_BASE);
  91. writeb(m, S6_REG_GPIO + S6_GPIO_IE);
  92. }
  93. static int set_type(struct irq_data *d, unsigned int type)
  94. {
  95. const u8 m = 1 << (d->irq - IRQ_BASE);
  96. irq_flow_handler_t handler;
  97. u8 reg;
  98. if (type == IRQ_TYPE_PROBE) {
  99. if ((readb(S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_AFSEL) & m)
  100. || (readb(S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IE) & m)
  101. || readb(S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_DIR
  102. + S6_GPIO_MASK(irq - IRQ_BASE)))
  103. return 0;
  104. type = IRQ_TYPE_EDGE_BOTH;
  105. }
  106. reg = readb(S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IS);
  107. if (type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_LEVEL_HIGH)) {
  108. reg |= m;
  109. handler = handle_level_irq;
  110. } else {
  111. reg &= ~m;
  112. handler = handle_edge_irq;
  113. }
  114. writeb(reg, S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IS);
  115. __irq_set_handler_locked(irq, handler);
  116. reg = readb(S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IEV);
  117. if (type & (IRQ_TYPE_LEVEL_HIGH | IRQ_TYPE_EDGE_RISING))
  118. reg |= m;
  119. else
  120. reg &= ~m;
  121. writeb(reg, S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IEV);
  122. reg = readb(S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IBE);
  123. if ((type & IRQ_TYPE_EDGE_BOTH) == IRQ_TYPE_EDGE_BOTH)
  124. reg |= m;
  125. else
  126. reg &= ~m;
  127. writeb(reg, S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IBE);
  128. return 0;
  129. }
  130. static struct irq_chip gpioirqs = {
  131. .name = "GPIO",
  132. .irq_ack = ack,
  133. .irq_mask = mask,
  134. .irq_unmask = unmask,
  135. .irq_set_type = set_type,
  136. };
  137. static u8 demux_masks[4];
  138. static void demux_irqs(unsigned int irq, struct irq_desc *desc)
  139. {
  140. struct irq_chip *chip = irq_desc_get_chip(desc);
  141. u8 *mask = irq_desc_get_handler_data(desc);
  142. u8 pending;
  143. int cirq;
  144. chip->irq_mask(&desc->irq_data);
  145. chip->irq_ack(&desc->irq_data));
  146. pending = readb(S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_MIS) & *mask;
  147. cirq = IRQ_BASE - 1;
  148. while (pending) {
  149. int n = ffs(pending);
  150. cirq += n;
  151. pending >>= n;
  152. generic_handle_irq(cirq);
  153. }
  154. chip->irq_unmask(&desc->irq_data));
  155. }
  156. extern const signed char *platform_irq_mappings[XTENSA_NR_IRQS];
  157. void __init variant_init_irq(void)
  158. {
  159. int irq, n;
  160. writeb(0, S6_REG_GPIO + S6_GPIO_BANK(0) + S6_GPIO_IE);
  161. for (irq = n = 0; irq < XTENSA_NR_IRQS; irq++) {
  162. const signed char *mapping = platform_irq_mappings[irq];
  163. int alone = 1;
  164. u8 mask;
  165. if (!mapping)
  166. continue;
  167. for(mask = 0; *mapping != -1; mapping++)
  168. switch (*mapping) {
  169. case S6_INTC_GPIO(0):
  170. mask |= 1 << 0;
  171. break;
  172. case S6_INTC_GPIO(1):
  173. mask |= 1 << 1;
  174. break;
  175. case S6_INTC_GPIO(2):
  176. mask |= 1 << 2;
  177. break;
  178. case S6_INTC_GPIO(3):
  179. mask |= 0x1f << 3;
  180. break;
  181. default:
  182. alone = 0;
  183. }
  184. if (mask) {
  185. int cirq, i;
  186. if (!alone) {
  187. printk(KERN_ERR "chained irq chips can't share"
  188. " parent irq %i\n", irq);
  189. continue;
  190. }
  191. demux_masks[n] = mask;
  192. cirq = IRQ_BASE - 1;
  193. do {
  194. i = ffs(mask);
  195. cirq += i;
  196. mask >>= i;
  197. irq_set_chip(cirq, &gpioirqs);
  198. irq_set_irq_type(irq, IRQ_TYPE_LEVEL_LOW);
  199. } while (mask);
  200. irq_set_handler_data(irq, demux_masks + n);
  201. irq_set_chained_handler(irq, demux_irqs);
  202. if (++n == ARRAY_SIZE(demux_masks))
  203. break;
  204. }
  205. }
  206. }