M3内核基本结构
- Cortex-M3内核是32位的
- M3F103内核采用Thumb-2指令集
- 支持16/32位指令混合编码
- 内核模式分为handler(管理者)和thread(线程)模式。handler运行在特权级下,thread可运行在特权级下和用户级下
- 操作权限分两个等级:特权级和用户级,处理器复位后自动进入thread模式下的特权级,这时候程序具有全部权限,处理器配置完毕后自动进入thread的用户级,放弃对重要处理器的配置权限。当进入中断时,自动切换到handler级。通过control寄存器的第0位可以切换特权级
- 内核有18个寄存器,R0-R12、R13为SP寄存器、R14为LR寄存器、R15为PC寄存器、XPSR寄存器
R0-R12作为通用寄存器,这些通用寄存器用来存放临时数据,R0-R3在程序调用时可以用来传递函数参数和返回值,R12在某些情况下可以用来 保存子程序的中间值
SP是栈寄存器,用来指示当前栈的位置。在M3中有两个SP寄存器分别为MSP和PSP。MSP为缺省的栈指针,handler模式只能用MSP,thread模式可以使用MSP和PSP。注意任何时刻只有一个SP起作用,可简单的只使用MSP。
LR是链接寄存器,用来保存跳转后返回的地址。当发生函数调用时,LR寄存器中保存着函数返回后需要执行的指令地址。LR对普通函数调用时存储调用函数后的返回地址,但在中断发生时发生了变化。
当中断发生时,硬件自动存储R0-R3,R12,LR,PC,XPSR这8个寄存器,中断返回时自动恢复这8个寄存器。中断发生时将这8个寄存器压入PSP/MSP栈,进入中断服务程序后,硬件会自动将一个特殊的值EXC_RETURN而不是返回地址存入LR中,EXC_RETURN只有三个值,0xFFFFFFF1表示中断服务程序返回handler模式且使用MSP,0xFFFFFFF9表示中断服务函数返回thread模式且使用MSP,0XFFFFFFFD表示中断服务函数返回thread模式且使用PSP。
中断时由于LR不保存返回地址,所以根据栈中的PC值(下条指令地址)来寻找入口。
可以理解为M3内核机制进行了一个二级跳,先将8个寄存器数值压入栈中,再将代表中断返回所使用的工作模式以及栈寄存器的EXC_RETURN值存入LR中,中断退出时跳转到EXC_RETURN值,并从栈中取出8个寄存器值,这样就不仅找到了返回地址,又可以找到中断前的工作状态和栈指针。
PC寄存器存储的是当前所执行指令所在的地址。处理器通过PC寄存器找到其需要执行的指令,更改PC寄存器就会发生指令跳转。
XPSR--状态寄存器,这个状态寄存器由多个寄存器复合而成。APSR存放着程序的状态,IPSR存放着中断号,EPSR存放着执行程序的状态。
STM32F103处理器运行的程序完全由这18个寄存器控制,操作系统通过备份、还原更改寄存器来控制程序执行流程,实现任务切换。
Thumb-2指令集
- 指令数:16条 指令空间:40byte 指令特点:16/32混合
- 数据计算指令:add、adr、sub
- 数据搬移指令:mov、ldr、ldm、stm、push、pop
- 状态寄存器操作指令:mrs、msr
- 逻辑计算指令:and
- 跳转指令:bx、xbz
- 软中断指令:svc
一个例子
testfunc1
PUSH {R4-R5}
LDR R0, =1
LDR R1, =2
LDR R2, =3
LDR R3, =4
LDR R4, =5
LDR R5, =6
PUSH{R4-R5,R14}
BL testfunc2
ADD R0,#7
ADD SP,#8
POP{R14}
POP{R4-R5}
BX R14
char testfunc2(char p1,char p2,char p3,char p4,char p5,char p6)
{
return p1 + p2 + p3 + p4 + p5 +p6;
}
该函数依次进行了,将R4,5压栈(0-3不压),R14(LR)压栈,计算testfunc2,恢复现场的操作。
函数间调用标准
该内核使用汇编语言编写寄存器相关代码,用c编写功能型代码
Arm内核上的规则是AAPCS
- 父函数与子函数间的入口参数通过R0-R3传递
- 子函数通过R0将函数值传递给父函数
- AAPCS规定,发生函数调用钱由父函数备份R0-R3寄存器中有用的数据
- R4-R11为普通的通用寄存器
- R13寄存器是SP,用来保存当前指针
- R14是连接寄存器,用来保存函数的返回地址
- R15是程序寄存器PC,正在执行的指令所在的地址存储在PC中
- XPSP寄存器是状态寄存器,某些指令会影响状态寄存器,用作判断