xref: /nrf52832-nimble/rt-thread/libcpu/ti-dsp/c28x/context.s (revision 104654410c56c573564690304ae786df310c91fc)
1;
2; Copyright (c) 2006-2018, RT-Thread Development Team
3;
4; SPDX-License-Identifier: Apache-2.0
5;
6; Change Logs:
7; Date           Author       Notes
8; 2018-09-01     xuzhuoyi     the first version.
9;
10
11    .ref   _rt_interrupt_to_thread
12    .ref   _rt_interrupt_from_thread
13    .ref   _rt_thread_switch_interrupt_flag
14
15    .def   _RTOSINT_Handler
16    .def   _rt_hw_get_st0
17    .def   _rt_hw_get_st1
18    .def   _rt_hw_context_switch_interrupt
19    .def   _rt_hw_context_switch
20    .def   _rt_hw_context_switch_to
21    .def   _rt_hw_interrupt_thread_switch
22    .def   _rt_hw_interrupt_disable
23    .def   _rt_hw_interrupt_enable
24
25
26RT_CTX_SAVE  .macro
27
28
29    PUSH    AR1H:AR0H
30    PUSH    XAR2
31    PUSH    XAR3
32    PUSH    XAR4
33    PUSH    XAR5
34    PUSH    XAR6
35    PUSH    XAR7
36    PUSH    XT
37    PUSH    RPC
38
39
40    .endm
41
42
43RT_CTX_RESTORE  .macro
44
45    POP     RPC
46    POP     XT
47    POP     XAR7
48    POP     XAR6
49    POP     XAR5
50    POP     XAR4
51    POP     XAR3
52    POP     XAR2
53
54
55    MOVZ    AR0 , @SP
56    SUBB    XAR0, #6
57    MOVL    ACC , *XAR0
58    AND     ACC, #0xFFFF << 16
59    MOV     AL, IER
60    MOVL   *XAR0, ACC
61
62
63    POP     AR1H:AR0H
64
65    .endm
66
67
68.text
69    .newblock
70
71;
72; rt_base_t rt_hw_interrupt_disable();
73;
74    .asmfunc
75_rt_hw_interrupt_disable:
76    DINT
77    LRETR
78    .endasmfunc
79
80;
81; void rt_hw_interrupt_enable(rt_base_t level);
82;
83    .asmfunc
84_rt_hw_interrupt_enable:
85    EINT
86    LRETR
87    .endasmfunc
88
89;
90; void rt_hw_context_switch(rt_uint32 from, rt_uint32 to);
91; r0 --> from
92; r4 --> to
93
94
95    .asmfunc
96_rt_hw_context_switch_interrupt:
97_rt_hw_context_switch:
98    MOVL    XAR0, #0
99    MOV     AR0, AL
100    MOVL    XAR4, *-SP[4]
101    ; set rt_thread_switch_interrupt_flag to 1
102    MOVL    XAR5, #_rt_thread_switch_interrupt_flag
103    MOVL    XAR6, *XAR5
104    MOVL    ACC, XAR6
105    CMPB    AL, #1
106    B       _reswitch, EQ
107    MOVL     XAR6, #1
108    MOVL    *XAR5, XAR6
109
110    MOVL    XAR5, #_rt_interrupt_from_thread   ; set rt_interrupt_from_thread
111    MOVL    *XAR5, XAR0
112
113_reswitch:
114    MOVL    XAR5, #_rt_interrupt_to_thread     ; set rt_interrupt_to_thread
115    MOVL    *XAR5, XAR4
116
117    TRAP    #16
118    LRETR
119    .endasmfunc
120
121     .asmfunc
122_RTOSINT_Handler:
123; disable interrupt to protect context switch
124    DINT
125
126    ; get rt_thread_switch_interrupt_flag
127    MOV     AR0, #_rt_thread_switch_interrupt_flag
128    MOV     AL, *AR0
129    MOV     AR1, AL
130    CMP     AR1, #0
131    B       rtosint_exit, EQ         ; pendsv already handled
132
133    ; clear rt_thread_switch_interrupt_flag to 0
134    MOV     AR1, #0x00
135    MOV     *AR0, AR1
136
137    MOV     AR0, #_rt_interrupt_from_thread
138    MOV     AL, *AR0
139    MOV     AR1, AL
140    CMP     AR1, #0
141    B       switch_to_thread, EQ    ; skip register save at the first time
142
143    ;MOVZ    AR1, @SP                 ; get from thread stack pointer
144
145;#if defined (__VFP_FP__) && !defined(__SOFTFP__)
146;    TST     lr, #0x10           ; if(!EXC_RETURN[4])
147;    VSTMDBEQ r1!, {d8 - d15}    ; push FPU register s16~s31
148;#endif
149
150    RT_CTX_SAVE     ; push r4 - r11 register
151
152;#if defined (__VFP_FP__) && !defined(__SOFTFP__)
153;    MOV     r4, #0x00           ; flag = 0
154
155;    TST     lr, #0x10           ; if(!EXC_RETURN[4])
156;    MOVEQ   r4, #0x01           ; flag = 1
157
158;    STMFD   r1!, {r4}           ; push flag
159;#endif
160
161    MOV     AL, *AR0
162    MOV     AR1, AL
163    MOVZ    AR1, @SP                 ; get from thread stack pointer
164    MOV     *AR0, AR1                ; update from thread stack pointer
165
166switch_to_thread:
167    MOV     AR1, #_rt_interrupt_to_thread
168    MOV     AL, *AR1
169    MOV     AR1, AL
170    MOV     AL, *AR1
171    MOV     AR1, AL                ; load thread stack pointer
172
173;#if defined (__VFP_FP__) && !defined(__SOFTFP__)
174;    LDMFD   r1!, {r3}           ; pop flag
175;#endif
176
177    MOV     @SP, AR1
178    INC     SP
179    RT_CTX_RESTORE     ; pop r4 - r11 register
180
181rtosint_exit:
182    ; restore interrupt
183    EINT
184
185    IRET
186    .endasmfunc
187
188    .asmfunc
189_rt_hw_get_st0:
190    PUSH    ST0
191    POP     AL
192    LRETR
193    .endasmfunc
194
195    .asmfunc
196_rt_hw_get_st1:
197    PUSH    ST1
198    POP     AL
199    LRETR
200    .endasmfunc
201
202;
203; * void rt_hw_context_switch_to(rt_uint32 to);
204; * r0 --> to
205
206    .asmfunc
207_rt_hw_context_switch_to:
208    MOV     AR1, #_rt_interrupt_to_thread
209    MOV     *AR1, AL
210
211;#if defined (__VFP_FP__) && !defined(__SOFTFP__)
212    ; CLEAR CONTROL.FPCA
213;    MRS     r2, CONTROL         ; read
214;    BIC     r2, #0x04           ; modify
215;    MSR     CONTROL, r2         ; write-back
216;#endif
217
218    ; set from thread to 0
219    MOV     AR1, #_rt_interrupt_from_thread
220    MOV     AR0, #0x0
221    MOV     *AR1, AR0
222
223    ; set interrupt flag to 1
224    MOV     AR1, #_rt_thread_switch_interrupt_flag
225    MOV     AR0, #1
226    MOV     *AR1, AR0
227
228    TRAP    #16
229
230
231    ; never reach here!
232    .endasmfunc
233
234; compatible with old version
235    .asmfunc
236_rt_hw_interrupt_thread_switch:
237    LRETR
238    NOP
239    .endasmfunc
240
241.end
242