【学习笔记】【ARM汇编】汇编语言学习

1、ARM 寻址方式

2、ARM 指令集

2.1 指令格式

<opcode>{<cond>}{S} <Rd>,<Rn>{,<opcode2>}

其中,<>内的项是必须的,{}内的项是可选的,如<opcode>是指令助记符,是必须的,而{<cond>}为指令
执行条件,是可选的,如果不写则使用默认条件AL(无条件执行)

opcode 指令助记符,如LDR,STR等
cond 执行条件,如EQ,NE等
S 是否影响CPSR寄存器的值,书写时影响CPSR,否则不影响
Rd 目标寄存器
Rn 第一个操作数的寄存器
operand2 第二个操作数
条件码助记符 标志 含义
EQ Z = 1 相等
NE Z = 0 不相等
CS/HS C = 1 无符号数大于或等于
CC/L0 C = 0 无符号数小于
MI N = 1 负数
PL N = 0 正数或零
VS V = 1 溢出
VC V = 0 没有溢出
HI C = 1, Z = 0 无符号数大于
LS C = 0, Z = 1 无符号数小于或等于
GE N = V 带符号数大于或等于
LT N != V 带符号数小于
GT Z = 0, N = V 带符号数大于
LE Z = 1, N != V 带符号数小于或等于
AL 任何 无条件执行(指令默认条件)

2.2 ARM 存储器访问指令

ARM处理是加载/存储体系结构的典型的RISC处理器,对存储器的访问只能使用加载和存储指令实现。ARM的加载/存储指令是可以实现字、半字,无符/有符字节操作;批量加载/存储指令可实现一条指令加载/存储多个寄存器的内容,大大提高效率;SWP指令是一条寄存器和存储器内容交换的指令,可用于信号量操作等。ARM处理器是冯.诺依曼存储结构,程序空间、RAM空间及IO映射空间统一编址,除对对RAM操作以外,对外围IO、程序数据的访问均要通过加载/存储指令进行

2.2.1 LDR 和 STR

加载/存储字和无符号字节指令.使用单一数据传送指令(STR和LDR)来装载和存储单一字节或字的数据从/到内存.
LDR指令用于从内存中读取数据放入寄存器中;
STR指令用于将寄存器中的数据保存到内存

LDR{cond}{T} Rd,<地址>;加载指定地址上的数据(),放入Rd中
STR{cond}{T} Rd,<地址>;存储数据()到指定地址的存储单元,要存储的数据在Rd中
LDR{cond}B{T} Rd,<地址>;加载字节数据,放入Rd中,即Rd最低字节有效,24位清零
STR{cond}B{T} Rd,<地址>;存储字节数据,要存储的数据在Rd,最低字节有效

2.2.2 LDM 和 STM

批量加载/存储指令可以实现在一组寄存器和一块连续的内存单元之间传输数据.LDM为加载多个寄存器,STM为存储多个寄存器.允许一条指令传送16个寄存器的任何子集或所有寄存器

LDM{cond}<模式> Rn{!},reglist{^}
STM{cond}<模式> Rn{!},reglist{^}

2.2.3 SWP

寄存器和存储器交换指令.SWP指令用于将一个内存单元(该单元地址放在寄存器Rn中)的内容读取到一个寄存器Rd中,同时将另一个寄存器Rm的内容写入到该内存单元中.使用SWP可实现信号量操作.

SWP{cond}{B} Rd,Rm,[Rn]

2.3 ARM 数据处理指令

数据处理指令大致可分为3类;数据传送指令(如MOV、MVN),算术逻辑运算指令(如ADD,SUM,AND),比较指令(如CMP,TST).数据处理指令只能对寄存器的内容进行操作.所有ARM数据处理指令均可选择使用S后缀,以影响状态标志.比较指令CMP,CMN,TST和TEQ不需要后缀S,它们会直接影响状态标志.

2.3.1 数据传送指令

2.3.1.1 MOV

数据传送指令.将8位图立即数或寄存器(operant2)传送到目标寄存器Rd,可用于移位运算等操作

MOV{cond}{S} Rd,operand2
2.3.1.2 MVN

数据非传送指令.将8位图立即数或寄存器(operand2)按位取反后传送到目标寄存器(Rd),因为其具有取反功能,所以可以装载范围更广的立即数

MVN{cond}{S} Rd,operand2

2.3.2 算数逻辑运算指令

2.3.2.1 ADD
加法运算指令.将operand2数据与Rn的值相加,结果保存到Rd寄存器
ADD{cond}{S} Rd,Rn,operand2
2.3.2.2 SUB
减法运算指令.用寄存器Rn减去operand2.结果保存到Rd中
SUB{cond}{S} Rd,Rn,operand2
2.3.2.3 RSB
逆向减法指令.用寄存器operand2减法Rn,结果保存到Rd中
RSB{cond}{S} Rd,Rn,operand2
2.3.2.4 ADC
带进位加法指令.将operand2的数据与Rn的值相加,再加上CPSR中的C条件标志位.结果保存到Rd寄存器
ADC{cond}{S} Rd,Rn,operand2
2.3.2.5 SBC
带进位减法指令。用寄存器Rn减去operand2,再减去CPSR中的C条件标志位的非(即若C标志清零,则结果减去1),结果保存到Rd中
SCB{cond}{S}Rd,Rn,operand2
2.3.2.6 RSC
带进位逆向减法指令.用寄存器operand2减去Rn,再减去CPSR中的C条件标志位,结果保存到Rd中
RSC{cond}{S} Rd,Rn,operand2
2.3.2.7 AND
逻辑与操作指令.将operand2值与寄存器Rn的值按位作逻辑与操作,结果保存到Rd中
AND{cond}{S} Rd,Rn,operand2
2.3.2.8 ORR
逻辑或操作指令.将operand2的值与寄存器Rn的值按位作逻辑或操作,结果保存到Rd中
ORR{cond}{S} Rd,Rn,operand2
2.3.2.9 EOR
逻辑异或操作指令.将operand2的值与寄存器Rn的值按位作逻辑异或操作,结果保存到Rd中
EOR{cond}{S}Rd,Rn,operand2
2.3.2.10 BIC
位清除指令.将寄存器Rn的值与operand2的值的反码按位作逻辑与操作,结果保存到Rd中
BIC{cond}{S}Rd,Rn,operand2

2.3.3 比较指令

2.3.3.1 CMP
比较指令.指令使用寄存器Rn的值减去operand2的值,根据操作的结果理新CPSR中的相应条件标志位,以便后面的指令根据相应的条件标志来判断是否执行
CMP{cond} Rn,operand2
2.3.3.2 CMN
负数比较指令.指令使用寄存器Rn与值加上operand2的值,根据操作的结果理新CPSR中的相应条件标志位,以便后面的指令根据相应的条件标志来判断是否执行
CMN{cond} Rn,operand2
2.3.3.3 TST
位测试指令.指令将寄存器Rn的值与operand2的值按位作逻辑与操作,根据操作的结果理新CPSR中相应的条件标志位,以便后面指令根据相应的条件标志来判断是否执行
TST{cond} Rn,operand2
2.3.3.4 TEQ
相等测试指令.指令寄存器Rn的值与operand2的值按位作逻辑异或操作,根据操作的结果理新CPSR中相应条件标志位,以便后面的指令根据相应的条件标志来判断是否执行
TEQ{cond} Rn,operand2

2.3.4 乘法指令

2.3.4.1 MUL
32位乘法指令.指令将Rm和Rs中的值相乘,结果的低32位保存到Rd中
MUL{cond}{S} Rd,Rm,Rs
2.3.4.2 MLA
32位乘加指令.指令将Rm和Rs中的值相乘,再将乘积加上第3个操作数,结果的低32位保存到Rd中
MLA{cond}{S} Rd,Rm,Rs,Rn
2.3.4.3 UMULL
64位无符号乘法指令.指令将Rm和Rs中的值作无符号数相乘,结果的低32位保存到RsLo中,而高32位保存到RdHi中
UMULL{cond}{S} RdLo,RdHi,Rm,Rs
2.3.4.4 UMLAL
64位无符号乘加指令.指令将Rm和Rs中的值作无符号数相乘,64位乘积与RdHi,RdLo相加,结果的低32位保存到RdLo中,而高32位保存到RdHi中
UMLAL{cond}{S} RdLo,RdHi,Rm,Rs
2.3.4.5 SMULL
64位有符号乘法指令.指令将Rm和Rs中的值作有符号数相乘,结果的低32位保存到RdLo中,而高32位保存到RdHi中
SMULL{cond}{S} RdLo,RdHi,Rm,Rs
2.3.4.6 SMLAL
64位有符号乘加指令.指令将Rm和Rs中的值作有符号数相乘,64位乘积与RdHi,RdLo,相加,结果的低32位保存到
RdLo中,而高32位保存到RdHi中
SMLAL{cond}{S} RdLo,RdHi,Rm,Rs

2.4 ARM 跳转指令

在ARM中有两种方式可以实现程序的跳转,一种是使用跳转指令直接跳转,另一种则是直接向PC寄存器赋值实现跳转.跳转指令有跳转指令B,带链接的跳转指令BL带状态切换的跳转指令BX

2.4.1 B

跳转指令.跳转到指定的地址执行程序
B{cond} label

2.4.2 BL

带链接的跳转指令.指令将下一条指令的地址拷贝到R14(即LR)链接寄存器中,然后跳转到指定地址运行程序
BL{cond} label

2.4.3 BX

带状态切换的跳转指令.跳转到Rm指定的地址执行程序,若Rm的位[0]1,则跳转时自动将CPSR中的标志T置位,
即把目标地址的代码解释为Thumb代码;若Rm的位[0]0,则跳转时自动将CPSR中的标志T复位,即把目标地址
的代码解释为ARM代码
BX{cond} Rm

2.5 ARM 协处理器指令

2.5.1 CDP

协处理器数据操作指令.ARM处理器通过CDP指令通知ARM协处理器执行特定的操作.该操作由协处理器完成,
即对命令的参数的解释与协处理器有关,指令的使用取决于协处理器.若协处理器不能成功地执行该操作,
将产生未定义指令异常中断
CDP{cond} coproc,opcodel,CRd,CRn,CRm{,opcode2}

2.5.2 LDC

协处理器数据读取指令.LDC指令从某一连续的内存单元将数据读取到协处理器的寄存器中.协处理器数据的数
据的传送,由协处理器来控传送的字数.若协处理器不能成功地执行该操作,将产生未定义指令异常中断
LDC{cond}{L} coproc,CRd,<地址>

2.5.3 STC

协处理器数据写入指令.STC指令将协处理器的寄存器数据写入到某一连续的内存单元中.进行协
处理器数据的数据传送,由协处理器来控制传送的字数.若协处理器不能成功地执行该操作,将产
生未定义指令异常中断
STC{cond}{L} coproc,CRd,<地址>

2.5.4 MCR

ARM寄存器到协处理器寄存器的数据传送指令.MCR指令将ARM处理器的寄存器中的数据传送到协处理器的
寄存器中.若协处理器不能成功地执行该操作,将产生未定义指令异常中断
MCR{cond} coproc,opcodel,Rd,CRn,CRm{,opcode2}

2.5.5 MRC

协处理器寄存器到ARM寄存器到的数据传送指令.MRC指令将协处理器寄存器中的数据传送到ARM处理器的
寄存器中.若协处理器不能成功地执行该操作.将产生未定义异常中断
MRC {cond} coproc,opcodel,Rd,CRn,CRm{,opcode2}

2.6 ARM 杂项指令

2.6.1 SWI

软中断指令.SWI指令用于产生软中断,从而实现在用户模式变换到管理模式,CPSR保存到管理模式的SPSR中,
执行转移到SWI向量,在其它模式下也可使用SWI指令,处理同样地切换到管理模式
SWI{cond} immed_24

2.6.2 MRS

读状态寄存器指令.在ARM处理器中,只有MRS指令可以状态寄存器CPSR或SPSR读出到通用寄存器中
MRS{cond} Rd ,psr
Rd 目标寄存器.Rd不允许为R15.
psr CPSR或SPSR

mrs	r0, cpsr      // 将 cpsr 状态寄存器读取保存到 r0

2.6.3 MSR

写状态寄存器指令.在ARM处理器中.只有MSR指令可以直接设置状态寄存器CPSR或SPSR
MSR{cond} psr_fields,#immed_8r
MSR{cond} psr_fields,Rm

2.7 ARM 伪指令

ARM伪指令不是ARM指令集中的指令,只是为了编程方便编译器定义了伪指令,使用时可以像其它ARM指令一样使用,但在编译时这些指令将被等效的ARM指令代替.ARM伪指令有四条,分别为ADR伪指令,ADRL伪指令,LDR伪指令,NOP伪指令.

2.7.1 ADR

小范围的地址读取伪指令.ADR指令将基于PC相对偏移的地址值读取到寄存器中.在汇编编译源程序时,ADR伪指
令被编译器替换成一条合适的指令.通常,编译器用一条ADD指令或SUB指令来实现该ADR伪指令的功能,若不能
用一条指令实现,则产生错误,编译失败.
ADR{cond} register,exper

2.7.2 ADRL

中等范围的地址读取伪指令.ADRL指令将基于PC相对偏移的地址值或基于寄存器相对偏移的地址值读取到寄存
器中,比ADR伪指令可以读取更大范围的地址。在汇编编译源程序时,ADRL伪指令被编译器替换成两个条合适
的指令。若不能用两条指令实现ADRL伪指令功能,则产生错误,编译失败
ADR{cond} register,exper

2.7.3 LDR

大范围的地址读取伪指令.LDR伪指令用于加载32位的立即数或一个地址值到指定寄存器.在汇编编译源程序时,
LDR伪指令被编译器替换成一条合适的指令.若加载的常数未超出MOV或MVN的范围,则使用MOV或MVN指令代替
该LDR伪指令,否则汇编器将常量放入字池,并使用一条程序相对偏移的LDR指令从文字池读出常量
LDR{cond} register,=expr/label_expr

2.7.4 NOP

空操作伪指令.NOP伪指令在汇编时将会被代替成ARM中的空操作,比如可能为MOV,R0,R0指令等
NOP

你可能感兴趣的:(学习,笔记,汇编)