ARM7处理器的七种模式:svc 这里主要探讨SVC模式和SYS模式。
SVC模式:通常是操作系统内核代码运行的模式,USR通常是用户代码运行模式。处理器一旦进入USR模式,必须通过SWI异常中断才能进入SVC模式调用内核代码的接口。但是在没有MMU进行内存保护的情况下,USR模式也能访问SVC模式的内存空间,因此用USR模式隔离用户级代码没有意义。
SYS模式:用于嵌套处理,一些关于ARM7编程指南认为,SYS模式是用于特权的操作系统代码运行模式,这种看法是错误的。它的正确用途是用于嵌套式中断。如果用IRQ/FIQ模式嵌套中断本身,则本模式的LR被改写后,本模式下原有的函数返回代码位置计数器数据就无法还原。
因此应该在关闭中断的条件下,在IRQ\FIQ模式中进行基本的环境准备后,让ISR切换到SYS模式下运行。这种处理方式保证产生嵌套中断时,被中断的模式是SYS模式而不是IRQ\FIQ模式自身,IRQ/FIQ模式中的LR保存着回到SYS模式的代码位置,SYS模式下LR未被破坏,保存着函数返回用的代码位置。
这是ARM V4版本之后增加SYS模式的原因,功能类似于USR模式,但是和SVC模式相互切换和访问(从这点上看,SYS模式是用于特权的操作系统代码运行模式),特别适合作为中断服务的模式。
需要注意的是,SYS模式和USR模式切换涉及到SWI功能的应用。简单移植中不使用USR和SYS两种模式。但是为了完成中断嵌套中断,可以使用UND模式替代SYS模式作为中断的运行模式。在没有MMU的ARM7中,正如前面讨论不必使用USR模式一样,采用SYS、SWI等功能仅仅是带入了复杂性,而没有其它好处。而且UND模式在没有协处理器的ARM7中同样没有用武之地,正好可以替换SYS模式使用。
完整任务切换代码:
OS_TASK_SW:
;在当前任务(被抢占任务)堆栈中保存当前任务环境
STMFD SP!, {LR} ;保存PC,LR中其实是任务切换时对应的PC值
STMFD SP!, {LR} ;保存LR
STMFD SP!, {r0-r12} ;保存寄存器和返回地址
MRS R0, CPSR ;保存CPSR
STMFD SP! {R0}
LDR R0, =i_pOSTCBCuR ;获取当前任务(被抢占任务)控制块地址,地址在R0
LDR R1, [R0] ;获取当前任务(被抢占任务)SP地址,在R1
STR SP, [R1] ;保存新SP到当前任务(被抢占任务)的TCB中
LDR R2, =g_pOSTCBHighRdy ;获取最高优先级任务控制块地址
LDR R1, [R2]
LDR R1, [R0] ;保存最高优先级任务地址到当前任务地址中(i_pOSTCBCur = )
LDR SP, [R0] ;获取新当前任务SP
;恢复任务环境
LDMFD SP!, {R0}
MSR SPSR_cxsf, R0
LDMFD SP! {R0-R12,LR,PC}^
//分析:恢复最高优先级任务环境:任务环境保存在堆栈中,SP指向任务堆栈的栈顶,通过先获取最高优先级任务控制(TCB)的地址,再得到SP的地址,从而恢复任务环境。
阅读(584) | 评论(0) | 转发(0) |