ARM裸机 - 嵌入式常用汇编总结

1.LDR(load register)指令将内存内容加载入通用寄存器

LDR R0,[R1];将存储器地址为R1的字数据读入寄存器R0。
LDR R0,[R1,R2];将存储器地址为R1+R2的字数据读入寄存器R0。
LDR R0,[R1,#8];将存储器地址为R1+8的字数据读入寄存器R0。
LDR R0,[R1],R2;将存储器地址为R1的字数据读入寄存器R0,并将R1+R2的值存入R1。
LDR R0,[R1],#8;将存储器地址为R1的字数据读入寄存器R0,并将R1+8的值存入R1。
LDR R0,[R1,R2]!;将存储器地址为R1+R2的字数据读入寄存器R0,并将R1+R2的值存入R1。
LDR R0,[R1,LSL #3];将存储器地址为R1*8的字数据读入寄存器R0。
LDR R0,[R1,R2,LSL #2];将存储器地址为R1+R2*4的字数据读入寄存器R0。
LDR R0,[R1,,R2,LSL #2]!;将存储器地址为R1+R2*4的字数据读入寄存器R0,并将R1+R2*4的值存入R1。
LDR R0,[R1],R2,LSL #2;将存储器地址为R1的字数据读入寄存器R0,并将R1+R2*4的值存入R1。
LDR R0,Label;Label为程序标号,Label必须是当前指令的-4~4KB范围内。

2.STR(store register)指令将寄存器内容存入内存空间中

STR R0,[R1],#8;将R0中的字数据写入以R1为地址的存储器中,并将新地址R1+8写入R1。
STR R0,[R1,#8];将R0中的字数据写入以R1+8为地址的存储器中。
str  r1, [r0];将r1寄存器的值,传送到地址值为r0的(存储器)内存中。

ARM裸机 - 嵌入式常用汇编总结_第1张图片

3. MOV是数据传送指令

用于将一个数据从源地址传送到目标地址(寄存器间的数据传送本质上也是一样的)。其特点是不破坏源地址单元的内容。
例如:
MOV AX,2000H;将16位数据2000H传送到AX寄存器
MOV AL,20H;将8位数据20H传送到AL寄存器
MOV AX,BX;将BX寄存器的16位数据传送到AX寄存器
MOV AL,[2000H];将2000H单元的内容传送到AL寄存器
需要注意的是:
(1)两个存储单元之间不能直接传送数据,即:MOV指令只允许一个操作数在存储器中。MOV [SI],[2000H];这是错误的
(2)MOV指令中立即数不能直接传送给段寄存器(CS、DS、SS、ES)和IP;段寄存器之间不能直接传送。MOV IP,2000 H ;这是错误的
(3)CS和IP不能作为目的操作数。MOV CS,AX ;这是错误的
(4)MOV指令中立即数不能作目标操作数。MOV 2000H,[SI] ;这是错误的

MOV指令可以在CPU内或CPU和存储器之间传送字或字节,它传送的信息可以从寄存器到寄存器,立即数到寄存器,立即数到存储单元,从存储单元到寄存器,从寄存器到存储单元,从寄存器或存储单元到除CS外的段寄存器(注意立即数不能直接送段寄存器),从段寄存器到寄存器或存储单元。
但是注意
*(1) MOV指令中的源操作数绝对不能是立即数和代码段CS寄存器;
(2) MOV指令中绝对不允许在两个存储单元之间直接传送数据;
(3) MOV指令中绝对不允许在两个段寄存器之间直接传送数据;
(4) MOV指令不会影响标志位*

4.算术运算符

ADD 指令将 Rn 中的值与 Operand2 中的值相加。
SUB 指令从 Rn 中的值中减去 Operand2 中的值。
RSB(反向减法)指令可从 Operand2 中的值减去 Rn 中的值。 这是很有用的,因为有了该指令,Operand2 的选项范围就会更大。
您可利用 ADC、SBC 和 RSC 来进行合成多字运算(请参阅多字算法示例)。
ADC(带进位加法)指令将 Rn 中的值和 Operand2 中的值相加(带进位标记)。
SBC(带进位减法)指令可从 Rn 中的值中减去 Operand2 中的值。 如果清除进位标记,则结果将减 1。
RSC(带进位反向减法)指令可从 Operand2 中的值中减去 Rn 中的值。 如果清除进位标记,则结果将减 1。

5.逻辑运算

位操作,运算操作
与 and r0 , #0xff //r0 &= 0xff
and r0 , r1 //r0 &= r1
或 orr r0 , #0xff //r0 |= 0xff
orr r0 , r1 //r0 &= r1
异或 eor r0 , r1 , #0xff //r0 = r1 ^ 0xff  //异或注意立即数只能出现在最后一个操作数,且最多只能有一个
取反 bic r0 , #0xff //r0 &= ~0xff
加  add r0 , r1 , r2 //r0 = r1 + r2
减  sub r0 , #4 //r0-=4

6.比较指令

cmp r0, r1  等价于 sub r2, r0, r1 (r2 = r0 - r1)
cmn r0, r1  等价于 add r0, r1
tst r0, #0xf 测试r0的bit0~bit3是否全为0
teq比较指令用来比较2个寄存器中的数
列:tst  r0, #0xf 测试bit0-bit3是否全为0;

7.CPSR寄存器访问指令(不可用mov访问)

mrs & msr
mrs 用来读psr (cpsr&spsr)
msr 用来写psr
mrs r0, cpsr 将cpsr的值读入到r0 处理r0的值
msr cpsr, r0 将r0的值写入到cpsr中
cpsr : 程序状态寄存器,CPU中只有一个,记录程序运行状态
spsr:CPU中有五个,分别在五种异常模式下,作用是从普通模式进入异常模式时,用来保存之前普通模式下的cpsr的,在返回普通模式时恢复原来的cpsr。

8.跳转指令

b & bl & bx
b 直接跳转(就没打开算返回)
bl branch and link,跳转前把返回地址放入lr中,以便返回,以便用于函数调用
bx跳转同时切换到ARM模式,一般用于异常处理的跳转。
B{条件} 目标地址。   BL{条件} 目标地址。

9.八种后缀

ia(increase after)先传输,再地址+4
ib(increase before)先地址+4,再传输
da(decrease after)先传输,再地址-4
db(decrease before)先地址-4,再传输
fd(full decrease)满递减堆栈
ed(empty decrease)空递减堆栈
fa(·······) 满递增堆栈
ea(·······)空递增堆栈

10.! 的作用

ldmia    r0, {r2 - r3}
ldmia    r0!, {r2 - r3}
感叹号的作用就是r0的值在ldm过程中发生的增加或者减少最后写回到r0去,也就是说ldm时会改变r0的值。
 

你可能感兴趣的:(ARM裸机)