irq-lpc32xx.c 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242
  1. // SPDX-License-Identifier: GPL-2.0-or-later
  2. /*
  3. * Copyright 2015-2016 Vladimir Zapolskiy <[email protected]>
  4. */
  5. #define pr_fmt(fmt) "%s: " fmt, __func__
  6. #include <linux/io.h>
  7. #include <linux/irqchip.h>
  8. #include <linux/irqchip/chained_irq.h>
  9. #include <linux/of_address.h>
  10. #include <linux/of_irq.h>
  11. #include <linux/of_platform.h>
  12. #include <linux/seq_file.h>
  13. #include <linux/slab.h>
  14. #include <asm/exception.h>
  15. #define LPC32XX_INTC_MASK 0x00
  16. #define LPC32XX_INTC_RAW 0x04
  17. #define LPC32XX_INTC_STAT 0x08
  18. #define LPC32XX_INTC_POL 0x0C
  19. #define LPC32XX_INTC_TYPE 0x10
  20. #define LPC32XX_INTC_FIQ 0x14
  21. #define NR_LPC32XX_IC_IRQS 32
  22. struct lpc32xx_irq_chip {
  23. void __iomem *base;
  24. phys_addr_t addr;
  25. struct irq_domain *domain;
  26. };
  27. static struct lpc32xx_irq_chip *lpc32xx_mic_irqc;
  28. static inline u32 lpc32xx_ic_read(struct lpc32xx_irq_chip *ic, u32 reg)
  29. {
  30. return readl_relaxed(ic->base + reg);
  31. }
  32. static inline void lpc32xx_ic_write(struct lpc32xx_irq_chip *ic,
  33. u32 reg, u32 val)
  34. {
  35. writel_relaxed(val, ic->base + reg);
  36. }
  37. static void lpc32xx_irq_mask(struct irq_data *d)
  38. {
  39. struct lpc32xx_irq_chip *ic = irq_data_get_irq_chip_data(d);
  40. u32 val, mask = BIT(d->hwirq);
  41. val = lpc32xx_ic_read(ic, LPC32XX_INTC_MASK) & ~mask;
  42. lpc32xx_ic_write(ic, LPC32XX_INTC_MASK, val);
  43. }
  44. static void lpc32xx_irq_unmask(struct irq_data *d)
  45. {
  46. struct lpc32xx_irq_chip *ic = irq_data_get_irq_chip_data(d);
  47. u32 val, mask = BIT(d->hwirq);
  48. val = lpc32xx_ic_read(ic, LPC32XX_INTC_MASK) | mask;
  49. lpc32xx_ic_write(ic, LPC32XX_INTC_MASK, val);
  50. }
  51. static void lpc32xx_irq_ack(struct irq_data *d)
  52. {
  53. struct lpc32xx_irq_chip *ic = irq_data_get_irq_chip_data(d);
  54. u32 mask = BIT(d->hwirq);
  55. lpc32xx_ic_write(ic, LPC32XX_INTC_RAW, mask);
  56. }
  57. static int lpc32xx_irq_set_type(struct irq_data *d, unsigned int type)
  58. {
  59. struct lpc32xx_irq_chip *ic = irq_data_get_irq_chip_data(d);
  60. u32 val, mask = BIT(d->hwirq);
  61. bool high, edge;
  62. switch (type) {
  63. case IRQ_TYPE_EDGE_RISING:
  64. edge = true;
  65. high = true;
  66. break;
  67. case IRQ_TYPE_EDGE_FALLING:
  68. edge = true;
  69. high = false;
  70. break;
  71. case IRQ_TYPE_LEVEL_HIGH:
  72. edge = false;
  73. high = true;
  74. break;
  75. case IRQ_TYPE_LEVEL_LOW:
  76. edge = false;
  77. high = false;
  78. break;
  79. default:
  80. pr_info("unsupported irq type %d\n", type);
  81. return -EINVAL;
  82. }
  83. irqd_set_trigger_type(d, type);
  84. val = lpc32xx_ic_read(ic, LPC32XX_INTC_POL);
  85. if (high)
  86. val |= mask;
  87. else
  88. val &= ~mask;
  89. lpc32xx_ic_write(ic, LPC32XX_INTC_POL, val);
  90. val = lpc32xx_ic_read(ic, LPC32XX_INTC_TYPE);
  91. if (edge) {
  92. val |= mask;
  93. irq_set_handler_locked(d, handle_edge_irq);
  94. } else {
  95. val &= ~mask;
  96. irq_set_handler_locked(d, handle_level_irq);
  97. }
  98. lpc32xx_ic_write(ic, LPC32XX_INTC_TYPE, val);
  99. return 0;
  100. }
  101. static void lpc32xx_irq_print_chip(struct irq_data *d, struct seq_file *p)
  102. {
  103. struct lpc32xx_irq_chip *ic = irq_data_get_irq_chip_data(d);
  104. if (ic == lpc32xx_mic_irqc)
  105. seq_printf(p, "%08x.mic", ic->addr);
  106. else
  107. seq_printf(p, "%08x.sic", ic->addr);
  108. }
  109. static const struct irq_chip lpc32xx_chip = {
  110. .irq_ack = lpc32xx_irq_ack,
  111. .irq_mask = lpc32xx_irq_mask,
  112. .irq_unmask = lpc32xx_irq_unmask,
  113. .irq_set_type = lpc32xx_irq_set_type,
  114. .irq_print_chip = lpc32xx_irq_print_chip,
  115. };
  116. static void __exception_irq_entry lpc32xx_handle_irq(struct pt_regs *regs)
  117. {
  118. struct lpc32xx_irq_chip *ic = lpc32xx_mic_irqc;
  119. u32 hwirq = lpc32xx_ic_read(ic, LPC32XX_INTC_STAT), irq;
  120. while (hwirq) {
  121. irq = __ffs(hwirq);
  122. hwirq &= ~BIT(irq);
  123. generic_handle_domain_irq(lpc32xx_mic_irqc->domain, irq);
  124. }
  125. }
  126. static void lpc32xx_sic_handler(struct irq_desc *desc)
  127. {
  128. struct lpc32xx_irq_chip *ic = irq_desc_get_handler_data(desc);
  129. struct irq_chip *chip = irq_desc_get_chip(desc);
  130. u32 hwirq = lpc32xx_ic_read(ic, LPC32XX_INTC_STAT), irq;
  131. chained_irq_enter(chip, desc);
  132. while (hwirq) {
  133. irq = __ffs(hwirq);
  134. hwirq &= ~BIT(irq);
  135. generic_handle_domain_irq(ic->domain, irq);
  136. }
  137. chained_irq_exit(chip, desc);
  138. }
  139. static int lpc32xx_irq_domain_map(struct irq_domain *id, unsigned int virq,
  140. irq_hw_number_t hw)
  141. {
  142. struct lpc32xx_irq_chip *ic = id->host_data;
  143. irq_set_chip_data(virq, ic);
  144. irq_set_chip_and_handler(virq, &lpc32xx_chip, handle_level_irq);
  145. irq_set_status_flags(virq, IRQ_LEVEL);
  146. irq_set_noprobe(virq);
  147. return 0;
  148. }
  149. static void lpc32xx_irq_domain_unmap(struct irq_domain *id, unsigned int virq)
  150. {
  151. irq_set_chip_and_handler(virq, NULL, NULL);
  152. }
  153. static const struct irq_domain_ops lpc32xx_irq_domain_ops = {
  154. .map = lpc32xx_irq_domain_map,
  155. .unmap = lpc32xx_irq_domain_unmap,
  156. .xlate = irq_domain_xlate_twocell,
  157. };
  158. static int __init lpc32xx_of_ic_init(struct device_node *node,
  159. struct device_node *parent)
  160. {
  161. struct lpc32xx_irq_chip *irqc;
  162. bool is_mic = of_device_is_compatible(node, "nxp,lpc3220-mic");
  163. const __be32 *reg = of_get_property(node, "reg", NULL);
  164. u32 parent_irq, i, addr = reg ? be32_to_cpu(*reg) : 0;
  165. irqc = kzalloc(sizeof(*irqc), GFP_KERNEL);
  166. if (!irqc)
  167. return -ENOMEM;
  168. irqc->addr = addr;
  169. irqc->base = of_iomap(node, 0);
  170. if (!irqc->base) {
  171. pr_err("%pOF: unable to map registers\n", node);
  172. kfree(irqc);
  173. return -EINVAL;
  174. }
  175. irqc->domain = irq_domain_add_linear(node, NR_LPC32XX_IC_IRQS,
  176. &lpc32xx_irq_domain_ops, irqc);
  177. if (!irqc->domain) {
  178. pr_err("unable to add irq domain\n");
  179. iounmap(irqc->base);
  180. kfree(irqc);
  181. return -ENODEV;
  182. }
  183. if (is_mic) {
  184. lpc32xx_mic_irqc = irqc;
  185. set_handle_irq(lpc32xx_handle_irq);
  186. } else {
  187. for (i = 0; i < of_irq_count(node); i++) {
  188. parent_irq = irq_of_parse_and_map(node, i);
  189. if (parent_irq)
  190. irq_set_chained_handler_and_data(parent_irq,
  191. lpc32xx_sic_handler, irqc);
  192. }
  193. }
  194. lpc32xx_ic_write(irqc, LPC32XX_INTC_MASK, 0x00);
  195. lpc32xx_ic_write(irqc, LPC32XX_INTC_POL, 0x00);
  196. lpc32xx_ic_write(irqc, LPC32XX_INTC_TYPE, 0x00);
  197. return 0;
  198. }
  199. IRQCHIP_DECLARE(nxp_lpc32xx_mic, "nxp,lpc3220-mic", lpc32xx_of_ic_init);
  200. IRQCHIP_DECLARE(nxp_lpc32xx_sic, "nxp,lpc3220-sic", lpc32xx_of_ic_init);