gic.h 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338
  1. /*
  2. * Copyright (c) 2019 Stephanos Ioannidis <root@stephanos.io>
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. */
  6. /**
  7. * @file
  8. * @brief Driver for ARM Generic Interrupt Controller
  9. *
  10. * The Generic Interrupt Controller (GIC) is the default interrupt controller
  11. * for the ARM A and R profile cores. This driver is used by the ARM arch
  12. * implementation to handle interrupts.
  13. */
  14. #ifndef ZEPHYR_INCLUDE_DRIVERS_GIC_H_
  15. #define ZEPHYR_INCLUDE_DRIVERS_GIC_H_
  16. /*
  17. * GIC Register Interface Base Addresses
  18. */
  19. #define GIC_DIST_BASE DT_REG_ADDR_BY_IDX(DT_INST(0, arm_gic), 0)
  20. #define GIC_CPU_BASE DT_REG_ADDR_BY_IDX(DT_INST(0, arm_gic), 1)
  21. /*
  22. * GIC Distributor Interface
  23. */
  24. /*
  25. * 0x000 Distributor Control Register
  26. * v1 ICDDCR
  27. * v2/v3 GICD_CTLR
  28. */
  29. #define GICD_CTLR (GIC_DIST_BASE + 0x0)
  30. /*
  31. * 0x004 Interrupt Controller Type Register
  32. * v1 ICDICTR
  33. * v2/v3 GICD_TYPER
  34. */
  35. #define GICD_TYPER (GIC_DIST_BASE + 0x4)
  36. /*
  37. * 0x008 Distributor Implementer Identification Register
  38. * v1 ICDIIDR
  39. * v2/v3 GICD_IIDR
  40. */
  41. #define GICD_IIDR (GIC_DIST_BASE + 0x8)
  42. /*
  43. * 0x080 Interrupt Group Registers
  44. * v1 ICDISRn
  45. * v2/v3 GICD_IGROUPRn
  46. */
  47. #define GICD_IGROUPRn (GIC_DIST_BASE + 0x80)
  48. /*
  49. * 0x100 Interrupt Set-Enable Reigsters
  50. * v1 ICDISERn
  51. * v2/v3 GICD_ISENABLERn
  52. */
  53. #define GICD_ISENABLERn (GIC_DIST_BASE + 0x100)
  54. /*
  55. * 0x180 Interrupt Clear-Enable Registers
  56. * v1 ICDICERn
  57. * v2/v3 GICD_ICENABLERn
  58. */
  59. #define GICD_ICENABLERn (GIC_DIST_BASE + 0x180)
  60. /*
  61. * 0x200 Interrupt Set-Pending Registers
  62. * v1 ICDISPRn
  63. * v2/v3 GICD_ISPENDRn
  64. */
  65. #define GICD_ISPENDRn (GIC_DIST_BASE + 0x200)
  66. /*
  67. * 0x280 Interrupt Clear-Pending Registers
  68. * v1 ICDICPRn
  69. * v2/v3 GICD_ICPENDRn
  70. */
  71. #define GICD_ICPENDRn (GIC_DIST_BASE + 0x280)
  72. /*
  73. * 0x300 Interrupt Set-Active Registers
  74. * v1 ICDABRn
  75. * v2/v3 GICD_ISACTIVERn
  76. */
  77. #define GICD_ISACTIVERn (GIC_DIST_BASE + 0x300)
  78. #if CONFIG_GIC_VER >= 2
  79. /*
  80. * 0x380 Interrupt Clear-Active Registers
  81. * v2/v3 GICD_ICACTIVERn
  82. */
  83. #define GICD_ICACTIVERn (GIC_DIST_BASE + 0x380)
  84. #endif
  85. /*
  86. * 0x400 Interrupt Priority Registers
  87. * v1 ICDIPRn
  88. * v2/v3 GICD_IPRIORITYRn
  89. */
  90. #define GICD_IPRIORITYRn (GIC_DIST_BASE + 0x400)
  91. /*
  92. * 0x800 Interrupt Processor Targets Registers
  93. * v1 ICDIPTRn
  94. * v2/v3 GICD_ITARGETSRn
  95. */
  96. #define GICD_ITARGETSRn (GIC_DIST_BASE + 0x800)
  97. /*
  98. * 0xC00 Interrupt Configuration Registers
  99. * v1 ICDICRn
  100. * v2/v3 GICD_ICFGRn
  101. */
  102. #define GICD_ICFGRn (GIC_DIST_BASE + 0xc00)
  103. /*
  104. * 0xF00 Software Generated Interrupt Register
  105. * v1 ICDSGIR
  106. * v2/v3 GICD_SGIR
  107. */
  108. #define GICD_SGIR (GIC_DIST_BASE + 0xf00)
  109. /*
  110. * GIC CPU Interface
  111. */
  112. #if CONFIG_GIC_VER <= 2
  113. /*
  114. * 0x0000 CPU Interface Control Register
  115. * v1 ICCICR
  116. * v2/v3 GICC_CTLR
  117. */
  118. #define GICC_CTLR (GIC_CPU_BASE + 0x0)
  119. /*
  120. * 0x0004 Interrupt Priority Mask Register
  121. * v1 ICCPMR
  122. * v2/v3 GICC_PMR
  123. */
  124. #define GICC_PMR (GIC_CPU_BASE + 0x4)
  125. /*
  126. * 0x0008 Binary Point Register
  127. * v1 ICCBPR
  128. * v2/v3 GICC_BPR
  129. */
  130. #define GICC_BPR (GIC_CPU_BASE + 0x8)
  131. /*
  132. * 0x000C Interrupt Acknowledge Register
  133. * v1 ICCIAR
  134. * v2/v3 GICC_IAR
  135. */
  136. #define GICC_IAR (GIC_CPU_BASE + 0xc)
  137. /*
  138. * 0x0010 End of Interrupt Register
  139. * v1 ICCEOIR
  140. * v2/v3 GICC_EOIR
  141. */
  142. #define GICC_EOIR (GIC_CPU_BASE + 0x10)
  143. /*
  144. * Helper Constants
  145. */
  146. /* GICC_CTLR */
  147. #define GICC_CTLR_ENABLEGRP0 BIT(0)
  148. #define GICC_CTLR_ENABLEGRP1 BIT(1)
  149. #define GICC_CTLR_ENABLE_MASK (GICC_CTLR_ENABLEGRP0 | GICC_CTLR_ENABLEGRP1)
  150. #if defined(CONFIG_GIC_V2)
  151. #define GICC_CTLR_FIQBYPDISGRP0 BIT(5)
  152. #define GICC_CTLR_IRQBYPDISGRP0 BIT(6)
  153. #define GICC_CTLR_FIQBYPDISGRP1 BIT(7)
  154. #define GICC_CTLR_IRQBYPDISGRP1 BIT(8)
  155. #define GICC_CTLR_BYPASS_MASK (GICC_CTLR_FIQBYPDISGRP0 | \
  156. GICC_CTLR_IRQBYPDISGRP1 | \
  157. GICC_CTLR_FIQBYPDISGRP1 | \
  158. GICC_CTLR_IRQBYPDISGRP1)
  159. #endif /* CONFIG_GIC_V2 */
  160. /* GICD_SGIR */
  161. #define GICD_SGIR_TGTFILT(x) ((x) << 24)
  162. #define GICD_SGIR_TGTFILT_CPULIST GICD_SGIR_TGTFILT(0b00)
  163. #define GICD_SGIR_TGTFILT_ALLBUTREQ GICD_SGIR_TGTFILT(0b01)
  164. #define GICD_SGIR_TGTFILT_REQONLY GICD_SGIR_TGTFILT(0b10)
  165. #define GICD_SGIR_CPULIST(x) ((x) << 16)
  166. #define GICD_SGIR_CPULIST_CPU(n) GICD_SGIR_CPULIST(BIT(n))
  167. #define GICD_SGIR_CPULIST_MASK 0xff
  168. #define GICD_SGIR_NSATT BIT(15)
  169. #define GICD_SGIR_SGIINTID(x) (x)
  170. #endif /* CONFIG_GIC_VER <= 2 */
  171. /* GICD_ICFGR */
  172. #define GICD_ICFGR_MASK BIT_MASK(2)
  173. #define GICD_ICFGR_TYPE BIT(1)
  174. /* GICD_TYPER.ITLinesNumber 0:4 */
  175. #define GICD_TYPER_ITLINESNUM_MASK 0x1f
  176. /*
  177. * Common Helper Constants
  178. */
  179. #define GIC_SGI_INT_BASE 0
  180. #define GIC_PPI_INT_BASE 16
  181. #define GIC_IS_SGI(intid) (((intid) >= GIC_SGI_INT_BASE) && \
  182. ((intid) < GIC_PPI_INT_BASE))
  183. #define GIC_SPI_INT_BASE 32
  184. #define GIC_SPI_MAX_INTID 1019
  185. #define GIC_IS_SPI(intid) (((intid) >= GIC_SPI_INT_BASE) && \
  186. ((intid) <= GIC_SPI_MAX_INTID))
  187. #define GIC_NUM_INTR_PER_REG 32
  188. #define GIC_NUM_CFG_PER_REG 16
  189. #define GIC_NUM_PRI_PER_REG 4
  190. /* GIC idle priority : value '0xff' will allow all interrupts */
  191. #define GIC_IDLE_PRIO 0xff
  192. /* Priority levels 0:255 */
  193. #define GIC_PRI_MASK 0xff
  194. /*
  195. * '0xa0'is used to initialize each interrtupt default priority.
  196. * This is an arbitrary value in current context.
  197. * Any value '0x80' to '0xff' will work for both NS and S state.
  198. * The values of individual interrupt and default has to be chosen
  199. * carefully if PMR and BPR based nesting and preemption has to be done.
  200. */
  201. #define GIC_INT_DEF_PRI_X4 0xa0a0a0a0
  202. /* GIC special interrupt id */
  203. #define GIC_INTID_SPURIOUS 1023
  204. /* Fixme: update from platform specific define or dt */
  205. #define GIC_NUM_CPU_IF CONFIG_MP_NUM_CPUS
  206. #ifndef _ASMLANGUAGE
  207. #include <zephyr/types.h>
  208. #include <device.h>
  209. /*
  210. * GIC Driver Interface Functions
  211. */
  212. /**
  213. * @brief Enable interrupt
  214. *
  215. * @param irq interrupt ID
  216. */
  217. void arm_gic_irq_enable(unsigned int irq);
  218. /**
  219. * @brief Disable interrupt
  220. *
  221. * @param irq interrupt ID
  222. */
  223. void arm_gic_irq_disable(unsigned int irq);
  224. /**
  225. * @brief Check if an interrupt is enabled
  226. *
  227. * @param irq interrupt ID
  228. * @return Returns true if interrupt is enabled, false otherwise
  229. */
  230. bool arm_gic_irq_is_enabled(unsigned int irq);
  231. /**
  232. * @brief Set interrupt priority
  233. *
  234. * @param irq interrupt ID
  235. * @param prio interrupt priority
  236. * @param flags interrupt flags
  237. */
  238. void arm_gic_irq_set_priority(
  239. unsigned int irq, unsigned int prio, unsigned int flags);
  240. /**
  241. * @brief Get active interrupt ID
  242. *
  243. * @return Returns the ID of an active interrupt
  244. */
  245. unsigned int arm_gic_get_active(void);
  246. /**
  247. * @brief Signal end-of-interrupt
  248. *
  249. * @param irq interrupt ID
  250. */
  251. void arm_gic_eoi(unsigned int irq);
  252. #ifdef CONFIG_SMP
  253. /**
  254. * @brief Initialize GIC of secondary cores
  255. */
  256. void arm_gic_secondary_init(void);
  257. #endif
  258. /**
  259. * @brief raise SGI to target cores
  260. *
  261. * @param sgi_id SGI ID 0 to 15
  262. * @param target_aff target affinity in mpidr form.
  263. * Aff level 1 2 3 will be extracted by api.
  264. * @param target_list bitmask of target cores
  265. */
  266. void gic_raise_sgi(unsigned int sgi_id, uint64_t target_aff,
  267. uint16_t target_list);
  268. #endif /* !_ASMLANGUAGE */
  269. #endif /* ZEPHYR_INCLUDE_DRIVERS_GIC_H_ */