1、处理器内部常用数据传输指令
MOV R0 R1 // 通用寄存器互传
MRS R0 CPSR // 特殊寄存器 向 通用寄存器传
MSR CPSR R1 // 通用寄存器 向 特殊寄存器传
2、存储指令的访问
ARM 不能直接访问 存储器
常用的 存储器 访问指令:
LDR 和 STR
LDR Rd, [Rn, #offset] 从存储器 Rn+offset 的位置读取数据存放到 Rd 中
STR Rd,[Rn, #offset] 将Rd中的数据 写入到存储器 Rn+ offset 位置
3、压栈 和 出栈
我们通常会在
A
函数中调用
B
函数,当
B
函数执行完以后再回到
A
函数继续执行。要想
再跳回
A
函数以后代码能够接着正常运行,那就必须在跳到
B
函数之前将当前处理器状态保存
起来
(
就是保存
R0~R15
这些寄存器值
)
,当
B
函数执行完成以后再用前面保存的寄存器值恢复
R0~R15 即可
保存 R0~R15 寄存器的操作就叫做
现场保护,
恢复 R0~R15 寄存器的操作就叫做
恢复现场
。在进行现场保护的时候需要进行
压栈(入栈)操作
,恢复现场就要进行出栈操作
压栈 的指令为 PUSH
,
出栈
的指令为
POP。
PUSH
POP
4.
跳转指令
①、直接使用跳转指令
B、BL
、
BX
等。
②、直接向
PC
寄存器里面写入数据。
1
、
B
指令
这是最简单的跳转指令,
B
指令会将
PC
寄存器的值设置为跳转目标地址, 一旦执行
B
指
令,
ARM
处理器就会立即跳转到指定的目标地址。如果要调用的函数不会再返回到原来的执行
处,那就可以用
B
指令,如下示例:
示例代码 7.2.4.1 B 指令示例
1
_start
:
2
3
ldr sp
,=
0X80200000
@
设置栈指针
4
b main
@
跳转到
main
函数
初始化了 SP 指针 有些处理器还需要做其他的初始化 比如初始化
DDR
为跳转到
C
文件以后再也不会回到汇编了,所以在第
4
行使用了
B
指令来完成跳转
这个时候就不能直接使用 B 指令了,因为 B 指令一旦跳转就再也不会回来了,这个时候要使用 BL 指令.
例代码 7.2.4.2 BL 指令示例
1
push
{
r0
,
r1
}
@
保存
r0,r1
2
cps #
0x13
@
进入
SVC
模式,允许其他中断再次进去
3
5
bl system_irqhandler
@
加载
C
语言中断处理函数到
r2
寄存器中
6
7
cps #
0x12
@
进入
IRQ
模式
8
pop
{
r0
,
r1
}
9
str r0
, [
r1
,
#
0X10
]
@
中断执行完成,写
EOIR
5.算术运算指令
ADD Rd, Rn, Rm
Rd = Rn + Rm
加法运算,指令为
ADD
ADD Rd, Rn, #immed
Rd = Rn + #immed
ADC Rd, Rn, Rm
Rd = Rn + Rm +
进位
带进位的加法运算,指令为
ADC
ADC Rd, Rn, #immed
Rd = Rn + #immed +
进位
SUB Rd, Rn, Rm
Rd = Rn – Rm
减法
SUB Rd, #immed
Rd = Rd - #immed
SUB Rd, Rn, #immed
Rd = Rn - #immed
SBC Rd, Rn, #immed
Rd = Rn - #immed –
借位
带借位的减法
SBC Rd, Rn ,Rm
Rd = Rn – Rm –
借位
MUL Rd, Rn, Rm
Rd = Rn * Rm
乘法
(32
位
)
UDIV Rd, Rn, Rm
Rd = Rn / Rm
无符号除法
SDIV Rd, Rn, Rm
Rd = Rn / Rm
有符号除法
嵌入式开发中最常会用的就是
加减指令
,乘除基本用不到。
AND Rd, Rn
Rd = Rd &Rn
按位与
AND Rd, Rn, #immed
Rd = Rn immed
AND Rd, Rn, Rm
Rd = Rn & Rm
ORR Rd, Rn
Rd = Rd | Rn
按位或
ORR Rd, Rn, #immed
Rd = Rn | #immed
ORR Rd, Rn, Rm
Rd = Rn | Rm
BIC Rd, Rn
Rd = Rd & (~Rn)
位清除
BIC Rd, Rn, #immed
Rd = Rn & (~#immed)
BIC Rd, Rn , Rm
Rd = Rn & (~Rm)
ORN Rd, Rn, #immed
Rd = Rn | (#immed)
按位或非
ORN Rd, Rn, Rm
Rd = Rn | (Rm)
EOR Rd, Rn
Rd = Rd ^ Rn
按位异或
EOR Rd, Rn, #immed
Rd = Rn ^ #immed
EOR Rd, Rn, Rm
Rd = Rn ^ Rm
学习
ARM
的所有指令请参考《
ARM ArchitectureReference Manual ARMv7-A and ARMv7-R edition.pdf
》和《
ARM Cortex-A(armV7)编 程手册 V4.0.pdf
》这两份文档。