「这是我参与11月更文挑战的第28天,活动详情查看:2021最后一次更文挑战」。
指令学习
传送指令
-
正常传送指令
mov
mov R0,#4 ;将4传送至R0寄存器
-
取反传送指令
mvn
,也叫数据非传送指令mvn R0,#4 ;将4取反后传送至R0寄存器 0100取反为1011
转移指令
- B指令
直接跳转,仅更改PC寄存器的值
示例:
B 0x00040000 ;直接跳转到物理地址0x00040000读取指令并执行
B 标号 ;直接跳转到标号处
- BL指令
跳转并链接,除了更改PC寄存器的值之外,还会将下一条指令所对应的物理地址存放至lr
寄存器中
示例:
BL 0x00040000
mov r1,3 ;假设这行指令对应物理地址为0x0040004, 那么BL一旦执行,会将该值存入lr寄存器
或者
BL 标号
-
BX指令
跳转并切换状态
BX指令后面只能跟寄存器,弥补了B指令和BL指令的不足, 同时会根据寄存器中最低比特位值切换ARM/Thumb模式
示例:
BL print
print
mov r1,#1
BX lr ;函数返回 如果R0[0]=1,则进入Thumb状态 反之进入ARM模式
除了通过指令来更改PC寄存器值之外,在ARM32中还可以直接使用传送指令对PC寄存器进行赋值:
mov pc,#0x00000008 ;往pc寄存器中写入一个地址值
mov R0,pc ;获取pc寄存器中的值
-
BLX指令
该指令将以下功能集于一身
-
更改PC寄存器的值
-
将下一条指令的地址存入lr寄存器
-
根据寄存器中最低比特位值切换ARM/Thumb模式
-
算术和逻辑运算指令
-
算术运算
add R0,#5 add R0,R1 ;加法 sub R0,#5 sub R0,R1 ;减法 mul R0,R1,R2 ;乘法指令, 这里至少三个寄存器参与 mla R0,R1,R2,R3 ;先乘后加 R0 = R1 × R2 + R3
-
逻辑运算
and R0.#3 and R0,R0 ;逻辑与 orr R0.#3 orr R0,R0 ;逻辑或 eor R0.#3 eor R0,R0 ;逻辑异或
移位指令
MOV R0, R1, LSL#2 ;将R1中的内容左移两位后传送到R0中。
MOV R0, R1, LSR#2 ;将R1中的内容右移两位后传送到R0中,左端用零来填充。
比较指令
-
比较两个值是否相等
cmp R0,R1 beq sub ;如果两个寄存器中的值相等则跳转到sub函数中,否则继续往下执行 sub cmp R0,#5 bne sub ;如果两个值不相等,跳转到sub函数,否则继续往下执行 sub
-
大于和小于(带符号)
;大于 cmp R0,R1 bgt sub ;如果R0寄存器中的值大于R1,则跳转至sub sub ;小于 cmp R0,R1 blt sub ;如果R0寄存器中的值大于R1,则跳转至sub sub
条件和循环伪指令
IF、ELSE 和 ENDIF
-
根据条件的成立与否决定是否执行某个程序段
-
IF、ELSE、ENDIF 伪指令可以嵌套使用
-
GBLL Test ;声明一个全局逻辑变量Test Test SETL {TRUE} IF Test = {TRUE} 程序段1 ELSE 程序段2 ENDIF
WHILE 和 WEND
-
根据条件的成立与否决定是否重复汇编一个程序段
-
若 WHILE 后面的逻辑表达式为真,则重复汇编该程序段,直到逻辑表达式为假
-
WHILE 和 WEND 伪指令可以嵌套使用
-
GBLA Counter ;声明一个全局数字变量Counter Counter SETA 3 ;赋值 ... WHILE Counter < 10 程序段 WEND