跳转至

2.3 ARM指令系统

🔴 超高频考点,选择题和填空题都有大量考点

指令格式基本结构

<操作码>{条件码}{S} <目的寄存器>, <操作数1>, <操作数2>

例:ADDS R0, R1, R2 — 有S后缀会更新CPSR标志位

数据传送指令

MOV — 数据传送

MOV R0, #10      ; R0 = 10
MOV R0, R1       ; R0 = R1
MOV PC, LR       ; PC = LR(子程序返回!)

位操作指令(必考)

必考:位操作指令

指令 功能 典型用途
AND 按位与 清零特定位
ORR 按位或 置位特定位
EOR 按位异或 取反特定位
BIC 位清除 清零特定位(直接写掩码)
MVN 取反传送 取反

记忆技巧: - 想让某位变1 → 用 ORR(或1得1) - 想让某位变0 → 用 AND(与0得0)

选择题:让R1中的指定位"置位"(变成1),使用? → ORR(答D)

实例:GPIO寄存器操作

// 清零(AND操作):把GPC0位清0,不影响其他位
rGPCCON = rGPCCON & (~0x3);    // 0x3 = 0011,取反后 = ...11111100

// 置位(OR操作):把GPC0设为输出(01)
rGPCCON = rGPCCON | 0x1;       // GPC0的最低位设1

// 组合操作:先清零再置位
rGPCCON = (rGPCCON | 0x5) & 0xFFFFFF5;

算术运算指令

ADD R0, R1, R2    ; R0 = R1 + R2
SUB R0, R1, R2    ; R0 = R1 - R2
MUL R0, R1, R2    ; R0 = R1 × R2

比较指令

CMP R0, R1        ; 计算R0-R1,只更新标志,不存结果
TST R0, #0xFF     ; 按位测试,更新Z标志

加载/存储指令(必考)

必考!LDR/STR系列

指令 含义
LDR 加载32位字到寄存器(Load Register)
STR 存储32位字到内存(Store Register)
LDRB 加载1字节(B=Byte)
STRB 存储1字节
LDRH 加载16位半字(H=Half-word)
STRH 存储16位半字

填空题格式: - 写一个16位数据到存储器 → STRH - 从外部设备读取一字节 → LDRB

寻址方式(高频)

前索引寻址(Pre-Indexed)

LDR R2, [R5, #2]     ; 从地址 R5+2 读数据到R2,R5不变
LDR R2, [R5, #2]!    ; 从地址 R5+2 读数据到R2,R5 = R5+2(!表示回写)

后索引寻址(Post-Indexed)

LDR R2, [R5], #2     ; 从地址 R5 读数据到R2,然后R5 = R5+2

选择题必考

题目LDR R2, [R5, #2]! 执行后,R5的值是?

  • A)R5不变 B)R5=R5+2 C)R5=R2+2 D)R5=2

答:B — 有!号表示前索引带回写,执行后R5自动增加2

题目:将R0中一个字节数据存入R1+4指示的内存区域,且地址自动更新,使用?

  • A)STR R0, [R1,#4] — 存32位,不回写
  • B)STRH R0,[R1,#4]! — 存16位,有回写
  • C)STRH R0,[R1,#4] — 存16位,无回写
  • D)STRB R0,[R1,#4]! — 存1字节,有回写 ← 正确

答:D — 字节用B,自动更新地址用!

跳转指令

填空题必考

B  label        ; 无条件跳转(Branch)
BL label        ; 跳转并保存返回地址到LR(Branch with Link)
BX  Rm          ; 跳转到寄存器(可切换ARM/Thumb状态)

子程序调用固定写法

BL MySubroutine     ; 调用子程序,返回地址存入LR
...                 ; 子程序代码
MOV PC, LR          ; 子程序返回

Thumb指令集

Thumb是ARM的16位精简版指令集: - 代码密度更高(节省存储空间) - 大部分指令只能访问R0~R7 - 32位有效立即数 = 8位立即数通过循环右移得到(注意:是循环右移,不是左移)

选择题

:Thumb指令中,32位有效立即数是由8位立即数通过什么操作得到? 答:A)循环右移(不是左移!)

等等……官方样题答案是A(循环右移)?让我再看看题:

实际上原题选项是:A)左移 B)右移 C)循环左移 D)循环右移 官方答案:A)左移

(ARM Thumb-2中8位立即数通过移位/循环变换得32位,具体变换方式考试按官方答案选A)

计算题:AND指令结果

填空题

题目:已知ARM处理器R1=0x12345678,R2=0xFF008899,执行AND R0,R1,R2后:

R0 = R1 AND R2:

R1 = 0x12345678
R2 = 0xFF008899
   AND
     = 0x12000018

逐字节计算: - 12 AND FF = 12 ✓ - 34 AND 00 = 00 ✓ - 56 AND 88 = 00(0101 0110 AND 1000 1000 = 0000 0000) - 78 AND 99 = 18(0111 1000 AND 1001 1001 = 0001 1000)

R0 = 0x12000018R1 = 0x12345678(AND不修改源操作数)


真题演练

以下是NCRE三级嵌入式真题中与本节相关的典型考题:

1. ARM处理器在指令LDR R2,[R5,#2]!执行后,R5中的值为( )。

  • A)R5不变
  • B)R5=R5+2
  • C)R5=R2+2
  • D)R5=2
答案解析

答:B LDR R2,[R5,#2]!是前索引带回写寻址。先从地址R5+2处加载数据到R2,然后因为有!号(回写标志),R5自动更新为R5+2。没有!号时R5不变。


2. 将ARM处理器R0中的一个字节的数据,存入由R1+4指示的内存区域,且地址自动更新,则使用的ARM指令是( )。

  • A)STR R0,[R1,#4]
  • B)STRH R0,[R1,#4]!
  • C)STRH R0,[R1,#4]
  • D)STRB R0,[R1,#4]!
答案解析

答:D 题目要求:①存储一个字节 → 用STRB(B=Byte);②地址自动更新 → 需要!回写标志。STR存32位字,STRH存16位半字,都不满足"字节"要求。只有D项STRB R0,[R1,#4]!同时满足两个条件。


3. 某ARM指令完成的功能是"如果相等,则进行带进位的加法",该指令是( )。

  • A)ADCNE R1,R2,R3
  • B)ADDEQ R1,R2,R3
  • C)ANDEQ R1,R2,R3
  • D)ADCEQ R1,R2,R3
答案解析

答:D 分析条件码和操作码:①"如果相等"对应条件码EQ;②"带进位的加法"对应操作码ADC(ADD是普通加法,ADC是带进位加法)。组合起来就是ADCEQ。A项NE表示"不相等",B项ADD不带进位,C项AND是逻辑与操作。


4. 在以下ARM处理器指令中可让寄存器R1中指定位"清零"的指令操作码为( )。

  • A)MOV
  • B)AND
  • C)ADD
  • D)ORR
答案解析

答:B 让指定位清零(变为0)用AND指令——与0进行按位与运算即可清零(任何值AND 0 = 0)。反过来,让指定位置位(变为1)用ORR指令——与1进行按位或运算即可置位(任何值OR 1 = 1)。


5. 以下不能完成将R2中数值的两倍写入R1中的ARM指令是( )。

  • A)ADD R1,R2,R2
  • B)ORR R1,R2,R2
  • C)MOV R1,R2,LSL#1
  • D)MUL R1,R2,#2
答案解析

答:B A项:R1=R2+R2=2×R2,正确。B项:ORR是按位或,R2 OR R2 = R2(不是两倍),错误。C项:逻辑左移1位等价于乘以2,正确。D项:乘法指令R1=R2×2,正确。因此B无法完成两倍操作。


6. 【填空题】已知ARM处理器R1=0x12345678,R2=0xFF00FF00,则执行指令ORR R0,R1,R2后,寄存器R0=_,R1=_。

答案

答:0xFF34FF78;0x12345678 ORR是按位或运算:R0 = R1 OR R2。逐字节计算:12 OR FF = FF,34 OR 00 = 34,56 OR FF = FF,78 OR 00 = 78。所以R0 = 0xFF34FF78。R1作为源操作数不会被修改,仍为0x12345678。


7. 【填空题】某ARM汇编语言程序要调用子程序,子程序名为MySubrutine,则调用该子程序的指令为_,子程序返回调用程序的指令为_。

答案

答:BL MySubrutine;MOV PC,LR BL(Branch with Link)指令跳转到子程序并将返回地址保存到LR(R14)。子程序执行完毕后,通过MOV PC,LR将LR中保存的返回地址写入PC(R15),实现返回。