1;/* 2; * FreeRTOS Kernel V10.6.2 3; * Copyright (C) 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved. 4; * 5; * SPDX-License-Identifier: MIT 6; * 7; * Permission is hereby granted, free of charge, to any person obtaining a copy of 8; * this software and associated documentation files (the "Software"), to deal in 9; * the Software without restriction, including without limitation the rights to 10; * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 11; * the Software, and to permit persons to whom the Software is furnished to do so, 12; * subject to the following conditions: 13; * 14; * The above copyright notice and this permission notice shall be included in all 15; * copies or substantial portions of the Software. 16; * 17; * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 18; * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 19; * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 20; * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 21; * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 22; * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23; * 24; * https://www.FreeRTOS.org 25; * https://github.com/FreeRTOS 26; * 27; */ 28 29 .text 30 .arm 31 .ref vTaskSwitchContext 32 .ref xTaskIncrementTick 33 .ref ulTaskHasFPUContext 34 .ref pxCurrentTCB 35 36;/*-----------------------------------------------------------*/ 37; 38; Save Task Context 39; 40portSAVE_CONTEXT .macro 41 DSB 42 43 ; Push R0 as we are going to use it 44 STMDB SP!, {R0} 45 46 ; Set R0 to point to the task stack pointer. 47 STMDB SP,{SP}^ 48 SUB SP, SP, #4 49 LDMIA SP!,{R0} 50 51 ; Push the return address onto the stack. 52 STMDB R0!, {LR} 53 54 ; Now LR has been saved, it can be used instead of R0. 55 MOV LR, R0 56 57 ; Pop R0 so it can be saved onto the task stack. 58 LDMIA SP!, {R0} 59 60 ; Push all the system mode registers onto the task stack. 61 STMDB LR,{R0-LR}^ 62 SUB LR, LR, #60 63 64 ; Push the SPSR onto the task stack. 65 MRS R0, SPSR 66 STMDB LR!, {R0} 67 68 .if (__TI_VFP_SUPPORT__) 69 ;Determine if the task maintains an FPU context. 70 LDR R0, ulFPUContextConst 71 LDR R0, [R0] 72 73 ; Test the flag 74 CMP R0, #0 75 76 ; If the task is not using a floating point context then skip the 77 ; saving of the FPU registers. 78 BEQ $+16 79 FSTMDBD LR!, {D0-D15} 80 FMRX R1, FPSCR 81 STMFD LR!, {R1} 82 83 ; Save the flag 84 STMDB LR!, {R0} 85 .endif 86 87 ; Store the new top of stack for the task. 88 LDR R0, pxCurrentTCBConst 89 LDR R0, [R0] 90 STR LR, [R0] 91 92 .endm 93 94;/*-----------------------------------------------------------*/ 95; 96; Restore Task Context 97; 98portRESTORE_CONTEXT .macro 99 LDR R0, pxCurrentTCBConst 100 LDR R0, [R0] 101 LDR LR, [R0] 102 103 .if (__TI_VFP_SUPPORT__) 104 ; The floating point context flag is the first thing on the stack. 105 LDR R0, ulFPUContextConst 106 LDMFD LR!, {R1} 107 STR R1, [R0] 108 109 ; Test the flag 110 CMP R1, #0 111 112 ; If the task is not using a floating point context then skip the 113 ; VFP register loads. 114 BEQ $+16 115 116 ; Restore the floating point context. 117 LDMFD LR!, {R0} 118 FLDMIAD LR!, {D0-D15} 119 FMXR FPSCR, R0 120 .endif 121 122 ; Get the SPSR from the stack. 123 LDMFD LR!, {R0} 124 MSR SPSR_CSXF, R0 125 126 ; Restore all system mode registers for the task. 127 LDMFD LR, {R0-R14}^ 128 129 ; Restore the return address. 130 LDR LR, [LR, #+60] 131 132 ; And return - correcting the offset in the LR to obtain the 133 ; correct address. 134 SUBS PC, LR, #4 135 .endm 136 137;/*-----------------------------------------------------------*/ 138; Start the first task by restoring its context. 139 140 .def vPortStartFirstTask 141 142vPortStartFirstTask: 143 portRESTORE_CONTEXT 144 145;/*-----------------------------------------------------------*/ 146; Yield to another task. 147 148 .def vPortYieldProcessor 149 150vPortYieldProcessor: 151 ; Within an IRQ ISR the link register has an offset from the true return 152 ; address. SWI doesn't do this. Add the offset manually so the ISR 153 ; return code can be used. 154 ADD LR, LR, #4 155 156 ; First save the context of the current task. 157 portSAVE_CONTEXT 158 159 ; Select the next task to execute. */ 160 BL vTaskSwitchContext 161 162 ; Restore the context of the task selected to execute. 163 portRESTORE_CONTEXT 164 165;/*-----------------------------------------------------------*/ 166; Yield to another task from within the FreeRTOS API 167 168 .def vPortYeildWithinAPI 169 170vPortYeildWithinAPI: 171 ; Save the context of the current task. 172 173 portSAVE_CONTEXT 174 ; Clear SSI flag. 175 MOVW R0, #0xFFF4 176 MOVT R0, #0xFFFF 177 LDR R0, [R0] 178 179 ; Select the next task to execute. */ 180 BL vTaskSwitchContext 181 182 ; Restore the context of the task selected to execute. 183 portRESTORE_CONTEXT 184 185;/*-----------------------------------------------------------*/ 186; Preemptive Tick 187 188 .def vPortPreemptiveTick 189 190vPortPreemptiveTick: 191 192 ; Save the context of the current task. 193 portSAVE_CONTEXT 194 195 ; Clear interrupt flag 196 MOVW R0, #0xFC88 197 MOVT R0, #0xFFFF 198 MOV R1, #1 199 STR R1, [R0] 200 201 ; Increment the tick count, making any adjustments to the blocked lists 202 ; that may be necessary. 203 BL xTaskIncrementTick 204 205 ; Select the next task to execute. 206 CMP R0, #0 207 BLNE vTaskSwitchContext 208 209 ; Restore the context of the task selected to execute. 210 portRESTORE_CONTEXT 211 212;------------------------------------------------------------------------------- 213 214 .if (__TI_VFP_SUPPORT__) 215 216 .def vPortInitialiseFPSCR 217 218vPortInitialiseFPSCR: 219 220 MOV R0, #0 221 FMXR FPSCR, R0 222 BX LR 223 224 .endif ;__TI_VFP_SUPPORT__ 225 226 227pxCurrentTCBConst .word pxCurrentTCB 228ulFPUContextConst .word ulTaskHasFPUContext 229;------------------------------------------------------------------------------- 230