?? os_cpu_a_backup.s
字號(hào):
LDR R11, [SP], #4
LDR R12, [SP], #4
LDR LR, [SP], #4
LDR PC, [SP], #4
;*********************************************************************************************************
; PERFORM A CONTEXT SWITCH (From interrupt level) - OSIntCtxSw()
;
; Note(s) : 1) OSIntCtxSw() is called in SYS mode with BOTH FIQ and IRQ interrupts DISABLED
;
; 2) The pseudo-code for OSCtxSw() is:
; a) OSTaskSwHook();
; b) OSPrioCur = OSPrioHighRdy;
; c) OSTCBCur = OSTCBHighRdy;
; d) SP = OSTCBHighRdy->OSTCBStkPtr;
; e) Restore the new task's context from the new task's stack
; f) Return to new task's code
;
; 3) Upon entry:
; OSTCBCur points to the OS_TCB of the task to suspend
; OSTCBHighRdy points to the OS_TCB of the task to resume
;*********************************************************************************************************
; RSEG CODE:CODE:NOROOT(2)
CODE32
OSIntCtxSw
BL OSTaskSwHook ; OSTaskSwHook();
LDR R4,=OSPrioCur ; OSPrioCur = OSPrioHighRdy
LDR R5,=OSPrioHighRdy
LDRB R6,[R5]
STRB R6,[R4]
LDR R4,=OSTCBCur ; OSTCBCur = OSTCBHighRdy;
LDR R6,=OSTCBHighRdy
LDR R6,[R6]
STR R6,[R4]
LDR SP,[R6] ; SP = OSTCBHighRdy->OSTCBStkPtr;
; RESTORE NEW TASK'S CONTEXT
LDR R4, [SP], #4 ; pop new task's CPSR
MSR CPSR_cxsf, R4
LDR R0, [SP], #4 ; pop new task's context
LDR R1, [SP], #4
LDR R2, [SP], #4
LDR R3, [SP], #4
LDR R4, [SP], #4
LDR R5, [SP], #4
LDR R6, [SP], #4
LDR R7, [SP], #4
LDR R8, [SP], #4
LDR R9, [SP], #4
LDR R10, [SP], #4
LDR R11, [SP], #4
LDR R12, [SP], #4
LDR LR, [SP], #4
LDR PC, [SP], #4
;*********************************************************************************************************
; IRQ Interrupt Service Routine
;*********************************************************************************************************
; RSEG CODE:CODE:NOROOT(2)
CODE32
OS_CPU_IRQ_ISR
STR R3, [SP, #-4]! ; PUSH WORKING REGISTERS ONTO IRQ STACK
STR R2, [SP, #-4]!
STR R1, [SP, #-4]!
MOV R1, SP ; Save IRQ stack pointer
ADD SP, SP,#12 ; Adjust IRQ stack pointer
SUB R2, LR,#4 ; Adjust PC for return address to task
MRS R3, SPSR ; Copy SPSR (i.e. interrupted task's CPSR) to R3
MSR CPSR_c, #(NO_INT | SYS32_MODE) ; Change to SYS mode
; SAVE TASK'S CONTEXT ONTO TASK'S STACK
STR R2, [SP, #-4]! ; Push task's Return PC
STR LR, [SP, #-4]! ; Push task's LR
STR R12, [SP, #-4]! ; Push task's R12-R4
STR R11, [SP, #-4]!
STR R10, [SP, #-4]!
STR R9, [SP, #-4]!
STR R8, [SP, #-4]!
STR R7, [SP, #-4]!
STR R6, [SP, #-4]!
STR R5, [SP, #-4]!
STR R4, [SP, #-4]!
LDR R4, [R1], #4 ; Move task's R1-R3 from IRQ stack to SYS stack
LDR R5, [R1], #4
LDR R6, [R1], #4
STR R6, [SP, #-4]!
STR R5, [SP, #-4]!
STR R4, [SP, #-4]!
STR R0, [SP, #-4]! ; Push task's R0 onto task's stack
STR R3, [SP, #-4]! ; Push task's CPSR (i.e. IRQ's SPSR)
; HANDLE NESTING COUNTER
LDR R0, =OSIntNesting ; OSIntNesting++;
LDRB R1, [R0]
ADD R1, R1,#1
STRB R1, [R0]
CMP R1, #1 ; if (OSIntNesting == 1) {
BNE OS_CPU_IRQ_ISR_1
LDR R4, =OSTCBCur ; OSTCBCur->OSTCBStkPtr = SP
LDR R5, [R4]
STR SP, [R5] ; }
OS_CPU_IRQ_ISR_1
MSR CPSR_c, #(NO_INT | IRQ32_MODE) ; Change to IRQ mode (to use the IRQ stack to handle interrupt)
BL OS_CPU_IRQ_ISR_Handler ; OS_CPU_IRQ_ISR_Handler();
MSR CPSR_c, #(NO_INT | SYS32_MODE) ; Change to SYS mode
BL OSIntExit ; OSIntExit();
; RESTORE TASK'S CONTEXT and RETURN TO TASK
LDR R4, [SP], #4 ; pop new task's CPSR
MSR CPSR_cxsf, R4
LDR R0, [SP], #4 ; pop new task's context
LDR R1, [SP], #4
LDR R2, [SP], #4
LDR R3, [SP], #4
LDR R4, [SP], #4
LDR R5, [SP], #4
LDR R6, [SP], #4
LDR R7, [SP], #4
LDR R8, [SP], #4
LDR R9, [SP], #4
LDR R10, [SP], #4
LDR R11, [SP], #4
LDR R12, [SP], #4
LDR LR, [SP], #4
LDR PC, [SP], #4
;FIQ NOT NEEDEDs !
;*********************************************************************************************************
; FIQ Interrupt Service Routine
;*********************************************************************************************************
; RSEG CODE:CODE:NOROOT(2)
; CODE32
;OS_CPU_FIQ_ISR
;
; STMFD SP!,{R1-R3} ; PUSH WORKING REGISTERS ONTO IRQ STACK
;
; MOV R1,SP ; Save IRQ stack pointer
;
; ADD SP,SP,#12 ; Adjust FIQ stack pointer
;
; SUB R2,LR,#4 ; Adjust PC for return address to task
;
; MRS R3,SPSR ; Copy SPSR (i.e. interrupted task's CPSR) to R3
;
; MSR CPSR_c,#(NO_INT | SYS32_MODE) ; Change to SYS mode
;
; ; SAVE TASK'S CONTEXT ONTO TASK'S STACK
; STMFD SP!,{R2} ; Push task's Return PC
; STMFD SP!,{R4-R12,LR} ; Push task's LR,R12-R4
; LDMFD R1!,{R4-R6} ; Move task's R1-R3 from IRQ stack to SYS stack
; STMFD SP!,{R4-R6}
; STMFD SP!,{R0} ; Push task's R0 onto task's stack
; STMFD SP!,{R3} ; Push task's CPSR (i.e. IRQ's SPSR)
;
; ; HANDLE NESTING COUNTER
; LDR R0,=OSIntNesting ; OSIntNesting++;
; LDRB R1,[R0]
; ADD R1,R1,#1
; STRB R1,[R0]
;
; CMP R1,#1 ; if (OSIntNesting == 1) {
; BNE OS_CPU_FIQ_ISR_1
;
; LDR R4,=OSTCBCur ; OSTCBCur->OSTCBStkPtr = SP
; LDR R5,[R4]
; STR SP,[R5] ; }
;OS_CPU_FIQ_ISR_1
; MSR CPSR_c,#(NO_INT | FIQ32_MODE) ; Change to FIQ mode (to use the FIQ stack to handle interrupt)
;
; BL OS_CPU_FIQ_ISR_Handler ; OS_CPU_FIQ_ISR_Handler();
;
; MSR CPSR_c,#(NO_INT | SYS32_MODE) ; Change to SYS mode
;
; BL OSIntExit ; OSIntExit();
;
; ; RESTORE TASK'S CONTEXT and RETURN TO TASK
; LDMFD SP!,{R4} ; pop new task's CPSR
; MSR CPSR_cxsf,r4
; LDMFD SP!,{R0-R12,LR,PC} ; pop new task's R0-R12,LR & PC
;
;
;;*********************************************************************************************************
;; POINTERS TO VARIABLES
;*********************************************************************************************************
; DATA
;=OS_IntNesting:
; DC32 OSIntNesting
;=OS_PrioCur:
; DC32 OSPrioCur
;=OS_PrioHighRdy:
; DC32 OSPrioHighRdy
;=OS_Running:
; DC32 OSRunning
;=OS_TCBCur:
; DC32 OSTCBCur
;=OS_TCBHighRdy:
; DC32 OSTCBHighRdy
END
?? 快捷鍵說(shuō)明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -