1
0

interrupt_gcc.S 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218
  1. /*
  2. * Copyright (c) 2019-Present Nuclei Limited. All rights reserved.
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. *
  6. * Change Logs:
  7. * Date Author Notes
  8. * 2020/03/26 hqfang First Nuclei RISC-V porting implementation
  9. */
  10. #include "riscv_encoding.h"
  11. .section .text.entry
  12. .align 8
  13. /**
  14. * \brief Global interrupt disabled
  15. * \details
  16. * This function disable global interrupt.
  17. * \remarks
  18. * - All the interrupt requests will be ignored by CPU.
  19. */
  20. .macro DISABLE_MIE
  21. csrc CSR_MSTATUS, MSTATUS_MIE
  22. .endm
  23. /**
  24. * \brief Macro for context save
  25. * \details
  26. * This macro save ABI defined caller saved registers in the stack.
  27. * \remarks
  28. * - This Macro could use to save context when you enter to interrupt
  29. * or exception
  30. */
  31. /* Save caller registers */
  32. .macro SAVE_CONTEXT
  33. csrrw sp, CSR_MSCRATCHCSWL, sp
  34. /* Allocate stack space for context saving */
  35. #ifndef __riscv_32e
  36. addi sp, sp, -20*REGBYTES
  37. #else
  38. addi sp, sp, -14*REGBYTES
  39. #endif /* __riscv_32e */
  40. STORE x1, 0*REGBYTES(sp)
  41. STORE x4, 1*REGBYTES(sp)
  42. STORE x5, 2*REGBYTES(sp)
  43. STORE x6, 3*REGBYTES(sp)
  44. STORE x7, 4*REGBYTES(sp)
  45. STORE x10, 5*REGBYTES(sp)
  46. STORE x11, 6*REGBYTES(sp)
  47. STORE x12, 7*REGBYTES(sp)
  48. STORE x13, 8*REGBYTES(sp)
  49. STORE x14, 9*REGBYTES(sp)
  50. STORE x15, 10*REGBYTES(sp)
  51. #ifndef __riscv_32e
  52. STORE x16, 14*REGBYTES(sp)
  53. STORE x17, 15*REGBYTES(sp)
  54. STORE x28, 16*REGBYTES(sp)
  55. STORE x29, 17*REGBYTES(sp)
  56. STORE x30, 18*REGBYTES(sp)
  57. STORE x31, 19*REGBYTES(sp)
  58. #endif /* __riscv_32e */
  59. .endm
  60. /**
  61. * \brief Macro for restore caller registers
  62. * \details
  63. * This macro restore ABI defined caller saved registers from stack.
  64. * \remarks
  65. * - You could use this macro to restore context before you want return
  66. * from interrupt or exeception
  67. */
  68. /* Restore caller registers */
  69. .macro RESTORE_CONTEXT
  70. LOAD x1, 0*REGBYTES(sp)
  71. LOAD x4, 1*REGBYTES(sp)
  72. LOAD x5, 2*REGBYTES(sp)
  73. LOAD x6, 3*REGBYTES(sp)
  74. LOAD x7, 4*REGBYTES(sp)
  75. LOAD x10, 5*REGBYTES(sp)
  76. LOAD x11, 6*REGBYTES(sp)
  77. LOAD x12, 7*REGBYTES(sp)
  78. LOAD x13, 8*REGBYTES(sp)
  79. LOAD x14, 9*REGBYTES(sp)
  80. LOAD x15, 10*REGBYTES(sp)
  81. #ifndef __riscv_32e
  82. LOAD x16, 14*REGBYTES(sp)
  83. LOAD x17, 15*REGBYTES(sp)
  84. LOAD x28, 16*REGBYTES(sp)
  85. LOAD x29, 17*REGBYTES(sp)
  86. LOAD x30, 18*REGBYTES(sp)
  87. LOAD x31, 19*REGBYTES(sp)
  88. /* De-allocate the stack space */
  89. addi sp, sp, 20*REGBYTES
  90. #else
  91. /* De-allocate the stack space */
  92. addi sp, sp, 14*REGBYTES
  93. #endif /* __riscv_32e */
  94. csrrw sp, CSR_MSCRATCHCSWL, sp
  95. .endm
  96. /**
  97. * \brief Macro for save necessary CSRs to stack
  98. * \details
  99. * This macro store MCAUSE, MEPC, MSUBM to stack.
  100. */
  101. .macro SAVE_CSR_CONTEXT
  102. /* Store CSR mcause to stack using pushmcause */
  103. csrrwi x0, CSR_PUSHMCAUSE, 11
  104. /* Store CSR mepc to stack using pushmepc */
  105. csrrwi x0, CSR_PUSHMEPC, 12
  106. /* Store CSR msub to stack using pushmsub */
  107. csrrwi x0, CSR_PUSHMSUBM, 13
  108. .endm
  109. /**
  110. * \brief Macro for restore necessary CSRs from stack
  111. * \details
  112. * This macro restore MSUBM, MEPC, MCAUSE from stack.
  113. */
  114. .macro RESTORE_CSR_CONTEXT
  115. LOAD x5, 13*REGBYTES(sp)
  116. csrw CSR_MSUBM, x5
  117. LOAD x5, 12*REGBYTES(sp)
  118. csrw CSR_MEPC, x5
  119. LOAD x5, 11*REGBYTES(sp)
  120. csrw CSR_MCAUSE, x5
  121. .endm
  122. /**
  123. * \brief Exception/NMI Entry
  124. * \details
  125. * This function provide common entry functions for exception/nmi.
  126. * \remarks
  127. * This function provide a default exception/nmi entry.
  128. * ABI defined caller save register and some CSR registers
  129. * to be saved before enter interrupt handler and be restored before return.
  130. */
  131. .section .text.trap
  132. /* In CLIC mode, the exeception entry must be 64bytes aligned */
  133. .align 6
  134. .global exc_entry
  135. exc_entry:
  136. /* Save the caller saving registers (context) */
  137. SAVE_CONTEXT
  138. /* Save the necessary CSR registers */
  139. SAVE_CSR_CONTEXT
  140. /*
  141. * Set the exception handler function arguments
  142. * argument 1: mcause value
  143. * argument 2: current stack point(SP) value
  144. */
  145. csrr a0, mcause
  146. mv a1, sp
  147. /*
  148. * TODO: Call the exception handler function
  149. * By default, the function template is provided in
  150. * system_Device.c, you can adjust it as you want
  151. */
  152. call core_exception_handler
  153. /* Restore the necessary CSR registers */
  154. RESTORE_CSR_CONTEXT
  155. /* Restore the caller saving registers (context) */
  156. RESTORE_CONTEXT
  157. /* Return to regular code */
  158. mret
  159. /**
  160. * \brief Non-Vector Interrupt Entry
  161. * \details
  162. * This function provide common entry functions for handling
  163. * non-vector interrupts
  164. * \remarks
  165. * This function provide a default non-vector interrupt entry.
  166. * ABI defined caller save register and some CSR registers need
  167. * to be saved before enter interrupt handler and be restored before return.
  168. */
  169. .section .text.irq
  170. /* In CLIC mode, the interrupt entry must be 4bytes aligned */
  171. .align 2
  172. .global irq_entry
  173. /* This label will be set to MTVT2 register */
  174. irq_entry:
  175. /* Save the caller saving registers (context) */
  176. SAVE_CONTEXT
  177. /* Save the necessary CSR registers */
  178. SAVE_CSR_CONTEXT
  179. /* This special CSR read/write operation, which is actually
  180. * claim the CLIC to find its pending highest ID, if the ID
  181. * is not 0, then automatically enable the mstatus.MIE, and
  182. * jump to its vector-entry-label, and update the link register
  183. */
  184. csrrw ra, CSR_JALMNXTI, ra
  185. /* Critical section with interrupts disabled */
  186. DISABLE_MIE
  187. /* Restore the necessary CSR registers */
  188. RESTORE_CSR_CONTEXT
  189. /* Restore the caller saving registers (context) */
  190. RESTORE_CONTEXT
  191. /* Return to regular code */
  192. mret
  193. /* Default Handler for Exceptions / Interrupts */
  194. .global default_intexc_handler
  195. Undef_Handler:
  196. default_intexc_handler:
  197. 1:
  198. j 1b