📄 switchtask.s
字号:
@;;
@;; miniTOS V0.1.3 1998-2003 (c) 林良水 (Lin LS)
@;; miniTOS是一个完全开放源码的软件,LGPL,但开发
@;;人员不保证本软件的可靠性,以及对您的损失负任何责任。
@;;
@;; 本文实现miniTOS 在arm上的进程调度。
@;;
@;; create by Lin LS ,1998.10
@;; 移植到Arm by Lin LS ,2000.8
@;; 修改优化AT9140800 by LinLS,2003
@;; 移植到skyeye by Linls,2005.6
@ INCLUDE aic.inc
#include "aic.h"
@ AREA |C$$Code|,CODE,READONLY
@ IMPORT ptrCurrProc
@ IMPORT SelectNewTask
.text
.align 2
.global begin_next_proc
.type begin_next_proc,function
begin_next_proc:
ldr r0,=ptrCurrProc @;now ptrCurrProc point to new TASK ProcTbl
ldr r0,[r0]
LDMFD r0!, {r1}
MSR SPSR_c, r1
LDMFD r0!, {r1}
MSR CPSR_c, r1
LDMFD r0!, {sp}
ldmfd r0!,{r1,r2} @;read ptrCurrProc[lr,pc]
stmfd sp!,{r1,r2} @;save ptrCurrProc[lr,pc] to stack
@;copy ptrCurrProc[r0-r12,lr,pc] to stack
LDMFD r0!,{r1-r12,lr} @;read ptrCurrProc[r0-r11,r12]
STMFD sp!,{r1-r12,lr} @;save ptrCurrProc[r0-r11,r12] to stack
LDMFD sp!, {r0-r12,lr,pc} @;begin select proc
@;TASK switch task by itself.(Notes:not INT)
@;
@ EXPORT switch_task
.global switch_task
.type switch_task,function
switch_task:
stmfd sp!,{r0} @;save r0 to stack
ldr r0,=ptrCurrProc @;Old Task ProcTbl
ldr r0,[r0]
add r0,r0,#18*4 @;ProcTbl bottom+1*4
stmdb r0!,{r1-r12} @;save r1--r12 to ProcTbl
mov r1,r0 @;r0==>r1
ldmfd sp!,{r0} @;get r0 from stack
stmdb r1!,{r0} @;save r0 to ProcTbl
stmfd r1!,{lr} @;lr==return pc,save pc,lr to ProcTbl
stmfd r1!,{lr}
stmfd r1!, {sp} @;save sp to ProcTbl
mrs r0, CPSR
stmdb r1!, {r0}
mrs r0, SPSR
stmdb r1!, {r0}
@;now sp is old TASK Stack
bl SelectNewTask
@;now ptrCurrProc point to new TASK
b begin_next_proc
@;-----------------------------------------------------------
@;Function: when irq is end,perhaps need to swtich task.
@;
@;-----------------------------------------------------------
@ EXPORT IRQ_switch_task
.global IRQ_switch_task
.type IRQ_switch_task,function
IRQ_switch_task:
mov r0,sp @;IRQ_SP to r0
add sp, sp, #(13 * 4) @;skip [r0--r12],now sp point to lr,sp-->lr
ldr r1,[sp] @;get lr (return address)
add sp, sp, #4 @;release stack of lr
@ ldr r6, =AIC_BASE @
@ str r6, [r6, #AIC_EOICR] @
@;
@;now r0=IRQ_sp (IRQ_stack pointer),r1=(lr)=(return to TASK address)
subs pc,pc, #0 @;now change to TASK mode(SVC_MODE)
@;spsr_IRQ==>CPSR
@;No IRQ,
mov r0,r0
mov r0,r0
mov r0,r0
mov r0,r0
@;now in TASK mode(SVC_MODE)
@;sp==TASK_SP(SVC_SP)
@;save register to ProcTbl
ldr r2,=ptrCurrProc @;Old Task ProcTbl
ldr r2,[r2]
mrs r3,spsr
stmia r2!,{r3} @;save spsr to procTbl
mrs r3,cpsr
stmia r2!,{r3} @;save cpsr to ProcTbl
stmia r2!,{sp} @;sp=TASK_sp
stmia r2!,{lr}
stmia r2!,{r1} @;IRQ return address ,pc
mov lr, r0 @;now lr=IRQ_sp
mov sp,r2
add sp,sp,#(13*4)
ldmia lr!,{r0-r12} @; get Irq_sp [r0..r12]
stmdb sp!,{r0-r12} @; bug ?????
@;
@;restore Old TASK sp
@;
ldr r0,=ptrCurrProc @;Old Task ProcTbl
ldr r0,[r0]
LDMFD r0!, {r1}
LDMFD r0!, {r1}
LDMFD r0!, {sp} @;get Old TASK sp
@;select a new task
bl SelectNewTask
@;now ptrCurrProc point to new TASK ProcTbl
b begin_next_proc @;now ptrCurrProc is the newest selected Process
@;The shell that entry the user proc
@ IMPORT ProcShell
@; IMPORT SignalShell
@ EXPORT ProcEntry
@; EXPORT SignalEntry
@ProcEntry:
@ DCD ProcShell
.global ProcEntry
.type ProcEntry,function
ProcEntry:
.word ProcShell
.global TisrEntry
.type TisrEntry,function
TisrEntry:
.word TisrShell
@ END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -