1#include <k_config.h> 2 3@****************************************************************************** 4@ EXTERN PARAMETERS 5@****************************************************************************** 6.extern g_active_task 7.extern g_preferred_ready_task 8.extern krhino_stack_ovf_check 9.extern krhino_task_sched_stats_get 10 11@****************************************************************************** 12@ EXPORT FUNCTIONS 13@****************************************************************************** 14.global cpu_intrpt_save 15.global cpu_intrpt_restore 16.global cpu_task_switch 17.global cpu_intrpt_switch 18.global cpu_first_task_start 19 20.global PendSV_Handler 21.global _first_task_restore 22 23@****************************************************************************** 24@ EQUATES 25@****************************************************************************** 26.equ SCB_ICSR, 0xE000ED04 @ Interrupt Control and State Register. 27.equ SCB_VTOR, 0xE000ED08 @ Vector Table Offset Register. 28.equ ICSR_PENDSVSET, 0x10000000 @ Value to trigger PendSV exception. 29 30.equ SHPR3_PRI_14, 0xE000ED22 @ System Handler Priority Register 3 (PendSV). 31.equ PRI_LVL_PENDSV, 0xFF @ PendSV priority level (lowest). 32.equ SHPR3_PRI_15, 0xE000ED23 @ System Handler Priority Register 3 (Systick). 33.equ PRI_LVL_SYSTICK, 0xFF @ SYstick priority level (lowest). 34 35@****************************************************************************** 36@ CODE GENERATION DIRECTIVES 37@****************************************************************************** 38.text 39.align 2 40.thumb 41.syntax unified 42 43@****************************************************************************** 44@ Functions: 45@ size_t cpu_intrpt_save(void); 46@ void cpu_intrpt_restore(size_t cpsr); 47@****************************************************************************** 48.thumb_func 49cpu_intrpt_save: 50 MRS R0, PRIMASK 51 CPSID I 52 BX LR 53 54.thumb_func 55cpu_intrpt_restore: 56 MSR PRIMASK, R0 57 BX LR 58 59@****************************************************************************** 60@ Functions: 61@ void cpu_intrpt_switch(void); 62@ void cpu_task_switch(void); 63@****************************************************************************** 64.thumb_func 65cpu_task_switch: 66 LDR R0, =SCB_ICSR 67 LDR R1, =ICSR_PENDSVSET 68 STR R1, [R0] 69 BX LR 70 71.thumb_func 72cpu_intrpt_switch: 73 LDR R0, =SCB_ICSR 74 LDR R1, =ICSR_PENDSVSET 75 STR R1, [R0] 76 BX LR 77 78@****************************************************************************** 79@ Functions: 80@ void cpu_first_task_start(void); 81@****************************************************************************** 82.thumb_func 83cpu_first_task_start: 84 @set PendSV prority to the lowest 85 LDR R0, =SHPR3_PRI_14 86 LDR R1, =PRI_LVL_PENDSV 87 STRB R1, [R0] 88 89 @set Systick prority to the lowest 90 LDR R0, =SHPR3_PRI_15 91 LDR R1, =PRI_LVL_SYSTICK 92 STRB R1, [R0] 93 94 @indicate PendSV_Handler branch to _pendsv_handler_nosave 95 MOVS R0, #0 96 MSR PSP, R0 97 98 @make PendSV exception pending 99 LDR R0, =SCB_ICSR 100 LDR R1, =ICSR_PENDSVSET 101 STR R1, [R0] 102 103 @goto PendSV_Handler 104 CPSIE I 105 B . 106 107@****************************************************************************** 108@ Functions: 109@ void krhino_pendsv_handler(void); 110@****************************************************************************** 111.thumb_func 112PendSV_Handler: 113 CPSID I 114 MRS R0, PSP 115 @branch if cpu_first_task_start 116 CMP R0, #0 117 BEQ _first_task_restore 118 119 @hardware saved R0~R3,R12,LR,PC,xPSR 120 121 @save context 122 #if (defined(__VFP_FP__) && !defined(__SOFTFP__)) 123 @if the switchout task use FPU, save the FPU regs 124 TST LR, #0x10 125 IT EQ 126 VSTMDBEQ R0!, {D8 - D15} 127 @hardware saved D0~D7, FPSCR 128 #endif 129 130 SUBS R0, R0, #0x24 131 STM R0, {R4-R11, LR} 132 133 @g_active_task->task_stack = context region 134 LDR R1, =g_active_task 135 LDR R1, [R1] 136 STR R0, [R1] 137 138#if (RHINO_CONFIG_TASK_STACK_OVF_CHECK > 0) 139 BL krhino_stack_ovf_check 140#endif 141#if (RHINO_CONFIG_SYS_STATS > 0) 142 BL krhino_task_sched_stats_get 143#endif 144 145.thumb_func 146_pendsv_handler_nosave: 147 LDR R0, =g_active_task 148 LDR R1, =g_preferred_ready_task 149 LDR R2, [R1] 150 STR R2, [R0] 151 @R0 = g_active_task->task_stack = context region 152 LDR R0, [R2] 153 154 @restore context 155 LDM R0, {R4-R11, LR} 156 ADDS R0, R0, #0x24 157 158 #if (defined(__VFP_FP__) && !defined(__SOFTFP__)) 159 @if the switchin task use FPU, save the FPU regs 160 TST LR, #0x10 161 IT EQ 162 VLDMIAEQ R0!, {D8 - D15} 163 @hardware will restore D0~D7, FPSCR 164 #endif 165 166 @return stack = PSP 167 MSR PSP, R0 168 169 CPSIE I 170 @hardware restore R0~R3,R12,LR,PC,xPSR 171 BX LR 172 173.thumb_func 174_first_task_restore: 175 @set MSP to the base of system stack 176 LDR R0, =SCB_VTOR 177 LDR R0, [R0] 178 LDR R0, [R0] 179 MSR MSP, R0 180 181 B _pendsv_handler_nosave 182 183.end 184 185