smccc_macros.S 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241
  1. /*
  2. * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved.
  3. *
  4. * SPDX-License-Identifier: BSD-3-Clause
  5. */
  6. #ifndef SMCCC_MACROS_S
  7. #define SMCCC_MACROS_S
  8. #include <arch.h>
  9. /*
  10. * Macro to save the General purpose registers (r0 - r12), the banked
  11. * spsr, lr, sp registers and the `scr` register to the SMC context on entry
  12. * due a SMC call. The `lr` of the current mode (monitor) is expected to be
  13. * already saved. The `sp` must point to the `smc_ctx_t` to save to.
  14. * Additionally, also save the 'pmcr' register as this is updated whilst
  15. * executing in the secure world.
  16. */
  17. .macro smccc_save_gp_mode_regs
  18. /* Save r0 - r12 in the SMC context */
  19. stm sp, {r0-r12}
  20. mov r0, sp
  21. add r0, r0, #SMC_CTX_SP_USR
  22. #if ARM_ARCH_MAJOR == 7 && !defined(ARMV7_SUPPORTS_VIRTUALIZATION)
  23. /* Must be in secure state to restore Monitor mode */
  24. ldcopr r4, SCR
  25. bic r2, r4, #SCR_NS_BIT
  26. stcopr r2, SCR
  27. isb
  28. cps #MODE32_sys
  29. stm r0!, {sp, lr}
  30. cps #MODE32_irq
  31. mrs r2, spsr
  32. stm r0!, {r2, sp, lr}
  33. cps #MODE32_fiq
  34. mrs r2, spsr
  35. stm r0!, {r2, sp, lr}
  36. cps #MODE32_svc
  37. mrs r2, spsr
  38. stm r0!, {r2, sp, lr}
  39. cps #MODE32_abt
  40. mrs r2, spsr
  41. stm r0!, {r2, sp, lr}
  42. cps #MODE32_und
  43. mrs r2, spsr
  44. stm r0!, {r2, sp, lr}
  45. /* lr_mon is already saved by caller */
  46. cps #MODE32_mon
  47. mrs r2, spsr
  48. stm r0!, {r2}
  49. stcopr r4, SCR
  50. #else
  51. /* Save the banked registers including the current SPSR and LR */
  52. mrs r4, sp_usr
  53. mrs r5, lr_usr
  54. mrs r6, spsr_irq
  55. mrs r7, sp_irq
  56. mrs r8, lr_irq
  57. mrs r9, spsr_fiq
  58. mrs r10, sp_fiq
  59. mrs r11, lr_fiq
  60. mrs r12, spsr_svc
  61. stm r0!, {r4-r12}
  62. mrs r4, sp_svc
  63. mrs r5, lr_svc
  64. mrs r6, spsr_abt
  65. mrs r7, sp_abt
  66. mrs r8, lr_abt
  67. mrs r9, spsr_und
  68. mrs r10, sp_und
  69. mrs r11, lr_und
  70. mrs r12, spsr
  71. stm r0!, {r4-r12}
  72. /* lr_mon is already saved by caller */
  73. ldcopr r4, SCR
  74. #if ARM_ARCH_MAJOR > 7
  75. /*
  76. * Check if earlier initialization of SDCR.SCCD to 1
  77. * failed, meaning that ARMv8-PMU is not implemented,
  78. * cycle counting is not disabled and PMCR should be
  79. * saved in Non-secure context.
  80. */
  81. ldcopr r5, SDCR
  82. tst r5, #SDCR_SCCD_BIT
  83. bne 1f
  84. #endif
  85. /* Secure Cycle Counter is not disabled */
  86. #endif
  87. ldcopr r5, PMCR
  88. /* Check caller's security state */
  89. tst r4, #SCR_NS_BIT
  90. beq 2f
  91. /* Save PMCR if called from Non-secure state */
  92. str r5, [sp, #SMC_CTX_PMCR]
  93. /* Disable cycle counter when event counting is prohibited */
  94. 2: orr r5, r5, #PMCR_DP_BIT
  95. stcopr r5, PMCR
  96. isb
  97. 1: str r4, [sp, #SMC_CTX_SCR]
  98. .endm
  99. /*
  100. * Macro to restore the `smc_ctx_t`, which includes the General purpose
  101. * registers and banked mode registers, and exit from the monitor mode.
  102. * r0 must point to the `smc_ctx_t` to restore from.
  103. */
  104. .macro monitor_exit
  105. /*
  106. * Save the current sp and restore the smc context
  107. * pointer to sp which will be used for handling the
  108. * next SMC.
  109. */
  110. str sp, [r0, #SMC_CTX_SP_MON]
  111. mov sp, r0
  112. /*
  113. * Restore SCR first so that we access the right banked register
  114. * when the other mode registers are restored.
  115. */
  116. ldr r1, [r0, #SMC_CTX_SCR]
  117. stcopr r1, SCR
  118. isb
  119. /*
  120. * Restore PMCR when returning to Non-secure state
  121. */
  122. tst r1, #SCR_NS_BIT
  123. beq 2f
  124. /*
  125. * Back to Non-secure state
  126. */
  127. #if ARM_ARCH_MAJOR > 7
  128. /*
  129. * Check if earlier initialization SDCR.SCCD to 1
  130. * failed, meaning that ARMv8-PMU is not implemented and
  131. * PMCR should be restored from Non-secure context.
  132. */
  133. ldcopr r1, SDCR
  134. tst r1, #SDCR_SCCD_BIT
  135. bne 2f
  136. #endif
  137. /*
  138. * Restore the PMCR register.
  139. */
  140. ldr r1, [r0, #SMC_CTX_PMCR]
  141. stcopr r1, PMCR
  142. 2:
  143. /* Restore the banked registers including the current SPSR */
  144. add r1, r0, #SMC_CTX_SP_USR
  145. #if ARM_ARCH_MAJOR == 7 && !defined(ARMV7_SUPPORTS_VIRTUALIZATION)
  146. /* Must be in secure state to restore Monitor mode */
  147. ldcopr r4, SCR
  148. bic r2, r4, #SCR_NS_BIT
  149. stcopr r2, SCR
  150. isb
  151. cps #MODE32_sys
  152. ldm r1!, {sp, lr}
  153. cps #MODE32_irq
  154. ldm r1!, {r2, sp, lr}
  155. msr spsr_fsxc, r2
  156. cps #MODE32_fiq
  157. ldm r1!, {r2, sp, lr}
  158. msr spsr_fsxc, r2
  159. cps #MODE32_svc
  160. ldm r1!, {r2, sp, lr}
  161. msr spsr_fsxc, r2
  162. cps #MODE32_abt
  163. ldm r1!, {r2, sp, lr}
  164. msr spsr_fsxc, r2
  165. cps #MODE32_und
  166. ldm r1!, {r2, sp, lr}
  167. msr spsr_fsxc, r2
  168. cps #MODE32_mon
  169. ldm r1!, {r2}
  170. msr spsr_fsxc, r2
  171. stcopr r4, SCR
  172. isb
  173. #else
  174. ldm r1!, {r4-r12}
  175. msr sp_usr, r4
  176. msr lr_usr, r5
  177. msr spsr_irq, r6
  178. msr sp_irq, r7
  179. msr lr_irq, r8
  180. msr spsr_fiq, r9
  181. msr sp_fiq, r10
  182. msr lr_fiq, r11
  183. msr spsr_svc, r12
  184. ldm r1!, {r4-r12}
  185. msr sp_svc, r4
  186. msr lr_svc, r5
  187. msr spsr_abt, r6
  188. msr sp_abt, r7
  189. msr lr_abt, r8
  190. msr spsr_und, r9
  191. msr sp_und, r10
  192. msr lr_und, r11
  193. /*
  194. * Use the `_fsxc` suffix explicitly to instruct the assembler
  195. * to update all the 32 bits of SPSR. Else, by default, the
  196. * assembler assumes `_fc` suffix which only modifies
  197. * f->[31:24] and c->[7:0] bits of SPSR.
  198. */
  199. msr spsr_fsxc, r12
  200. #endif
  201. /* Restore the LR */
  202. ldr lr, [r0, #SMC_CTX_LR_MON]
  203. /* Restore the rest of the general purpose registers */
  204. ldm r0, {r0-r12}
  205. exception_return
  206. .endm
  207. #endif /* SMCCC_MACROS_S */