琢磨ucos内核进行中++>>>>>>>
先上cortex-M3 与本部分相关的汇编指令
相关的汇编指令
至于相关伪指令,参见:-----ARM汇编伪指令----
NVIC---Nested Vectored Interrupt controller--嵌套向量中断控制器
这里给出NVIC寄存器映射:
NVIC 空间还用来实现系统控制寄存器。NVIC 空间分成以下部分:
0xE000E000 - 0xE000E00F. 中断类型寄存器
0xE000E010 - 0xE000E0FF. 系统定时器
0xE000E100 - 0xE000ECFF. NVIC
0xE000ED00 -0xE000ED8F. 系统控制模块,包括:CPUID;系统控制、配置和状态;故障报告。
0xE000EF00 - 0xE000EF0F. 软件触发异常寄存器
0xE000EFD0 -0xE000EFFF. ID空间
详情查看:《cortex-M3技术参考手册》
另,关于Cortex-M3存储器结构和STM32存储器结构,参见 stm32存储器结构
这里关注如下寄存器:
留意标注的就好。
中断控制状态寄存器 :
中断控制状态寄存器用于:
设置一个挂起(pending)NMI
设置或清除一个挂起 SVC
设置或清除一个挂起 SysTick
查找挂起异常
查找最高优先级挂起异常的向量号
查找激活异常的向量号
寄存器地址、访问类型和复位状态:见上表
中断控制状态寄存器的位分配:
说明如下:
系统处理器优先级寄存器 :
通过 3 个处理器优先级寄存器为系统处理器排列优先级:
存储器管理
总线故障
使用故障
调试监控
SVC
SysTick
PendSV
系统处理器是一种特殊的异常处理器,它可以将自己的优先级设置成任意级别。大多数系统处理器都可以打开屏蔽(使能)或关闭屏蔽(禁能) 。禁能时,故障总是被当作硬故障。
寄存器地址、访问类型和复位状态:--见上边
系统处理器优先级寄存器的位分配:
下表描述了系统处理器优先级寄存器的各个位。
这里我们关注 PRI_11、PRI15、PRI_14==>SVCall异常、SysCall异常、PendSV异常。。。
以上只为更好的读懂、理解 OS_CPU_A.ASM ,,,
OS_CPU_A.ASM解析:
环境:
STM32 cortex-M3内核的片子 + ucos + IAR
@自己:coretex A8、A9都是armv7a 架构;coretex M3、M4是armv7m架构;前者是内核,后者是指令集的架构。
变量、函数声明 及 相关宏定义:有点像.h文件干的事。
;********************************************************************************************************
EXTERN OSRunning ; External references 全局变量声明,非本地定义
EXTERN OSPrioCur
EXTERN OSPrioHighRdy
EXTERN OSTCBCur
EXTERN OSTCBHighRdy
EXTERN OSIntNesting
EXTERN OSIntExit
EXTERN OSTaskSwHook
EXTERN OSRdyGrp
EXTERN OSRdyTbl
EXTERN OSPrioHighRdy
PUBLIC OS_CPU_SR_Save ; Functions declared in this file 公共函数声明
PUBLIC OS_CPU_SR_Restore
PUBLIC OSStartHighRdy
PUBLIC OSCtxSw
PUBLIC OSIntCtxSw
PUBLIC OS_CPU_PendSVHandler
;********************************************************************************************************
; EQUATES;宏定义
;********************************************************************************************************
NVIC_INT_CTRL EQU 0xE000ED04 ; Interrupt control state register.
NVIC_SYSPRI14 EQU 0xE000ED22 ; System priority register (priority 14).
NVIC_PENDSV_PRI EQU 0xFF ; PendSV priority value (lowest).
NVIC_PENDSVSET EQU 0x10000000 ; Value to trigger PendSV exception.
然后是--RSEG CODE:CODE:NOROOT(2)
RSEG CODE:CODE:NOROOT(2)
+
已经注释的OS_SchedNew 实现..
.................
原谅我看不太懂,,
提供线索如下,
处理关键代码段时开关中断:
CRITICAL SECTION METHOD 3 FUNCTIONS:关键代码段方法3函数
Description:通过保存中断的状态来禁用/启用中断。一般来说我们将中断禁用标志的状态存储在本地变量“cpu_sr”中然后禁用中断。我们能够恢复中断禁用状态通过复制回“cpu_sr”到CPU状态寄存器中。
;********************************************************************************************************
; CRITICAL SECTION METHOD 3 FUNCTIONS
;
; Description: Disable/Enable interrupts by preserving the state of interrupts. Generally speaking you
; would store the state of the interrupt disable flag in the local variable 'cpu_sr' and then
; disable interrupts. 'cpu_sr' is allocated in all of uC/OS-II's functions that need to
; disable interrupts. You would restore the interrupt disable state by copying back 'cpu_sr'
; into the CPU's status register.
;
; Prototypes : OS_CPU_SR OS_CPU_SR_Save(void);
; void OS_CPU_SR_Restore(OS_CPU_SR cpu_sr);
;
;
; Note(s) : 1) These functions are used in general like this:
;
; void Task (void *p_arg)
; {
; #if OS_CRITICAL_METHOD == 3 /* Allocate storage for CPU status register */
; OS_CPU_SR cpu_sr;
; #endif
;
; :
; :
; OS_ENTER_CRITICAL(); /* cpu_sr = OS_CPU_SaveSR(); */
; :
; :
; OS_EXIT_CRITICAL(); /* OS_CPU_RestoreSR(cpu_sr); */
; :
; :
; }
;********************************************************************************************************
OS_CPU_SR_Save
MRS R0, PRIMASK ; 读回PRIMASK寄存器内容
CPSID I
BX LR
OS_CPU_SR_Restore
MSR PRIMASK, R0
BX LR
PRIMASK寄存器: 除能所有的中断——当然了,不可屏蔽中断(NMI)不甩它。
OSStartHighRdy:
当OS初始化完毕后,执行OSStart,OSStart最后调用OSStartHighRdy函数,注意在此之前的线程模式和异常模式的堆栈都是MSP,在此之后线程模式的堆栈是PSP,异常模式的堆栈仍是MSP。
;********************************************************************************************************
; START MULTITASKING 开始任务
; void OSStartHighRdy(void)
;
; Note(s) : 1) This function triggers a PendSV exception (essentially, causes a context switch) to cause
; the first task to start.函数触发PendSV异常(从本质上讲,是导致上下文切换)导致第一个任务开始
;
; 2) OSStartHighRdy() MUST: 关键流程
; a) Setup PendSV exception priority to lowest;
; 设置PendSV异常优先级到最低
; b) Set initial PSP to 0, to tell context switcher this is first run;
; 设置初始进程堆栈到0位置,目的是告诉上下文/任务切换器这个函数第一个执行
; c) Set OSRunning to TRUE;
; 设置OSRunning标志为TRUE
; d) Trigger PendSV exception;
; 切换PendSV异常
; e) Enable interrupts (tasks will run with interrupts enabled).
; 使能中断(任务将通过启用中断运行)
;********************************************************************************************************
OSStartHighRdy
LDR
『本文转载自网络,版权归原作者所有,如有侵权请联系删除』