《stm32常用汇编指令》由会员分享,可在线阅读,更多相关《stm32常用汇编指令(7页珍藏版)》请在金锄头文库上搜索。
1、在嵌入式开发中,汇编程序常常用于非常关键的地方,比如系统启动时初始化,进出中断时 的环境保护,恢复等对性能有要求的地方。 ARM 指令集可以分为六大类,分别为数据处理指令、Load/Store 指令、跳转指令、程序状态 寄存器处理指令、协处理器指令和异常产生指令。 ARM 指令使用的基本格式如下: opcodecondSRd,Rn,operand2 opcode 操作码;指令助记符,如 LDR、STR 等。 cond 可选的条件码;执行条件,如 EQ、NE 等。 S 可选后缀;若指定“S”,则根据指令执行结果更新 CPSR 中的条件码。 Rd 目标寄存器。 Rn 存放第 1 操作数的寄存器。
2、operand2 第 2 个操作数 arm 的寻址方式如下: 立即寻址 寄存器寻址 寄存器间接寻址 基址加偏址寻址 堆栈寻址 块拷贝寻址 相对寻址 这里不作详细描述,可以查阅相关文档。 数据处理指令 Load/Store 指令 程序状态寄存器与通用寄存器之间的传送指令 转移指令 异常中断指令 协处理器指令 在 S3C2410、S3C2440 的数据手册中对各种汇编指令有详细的描述;这里只对较常见的作写 介绍。 1、相对跳转指令:b、bl 这两条指令的不同之处在于 bl 指令除了跳转之外,还将返回地址(bl 的下一条指令的地址) 保存在 lr 寄存器中。 这两条指令的可跳转范围是当前指令前后 3
3、2M。 b funa funa: b funb funb: 2、数据传送指令 mov,地址读取伪指令 ldr mov 指令可以把一个寄存器的值赋给另外一个寄存器,或者把一个常数赋给寄存器。 mov r1, r2 mov r1,#1024 mov 传送的常数必须能用立即数来表示。当不能用立即数表示时,可以用 ldr 命令来赋值。 ldr 是伪命令, 不是真实存在的指令, 编译器会把它扩展成真正的指令; 如果该常数能用 “立 即数”来表示,则使用 mov 指令,否则编译时将该常数保存在某个位置,使用内存读取指令 把它读出来。 ldr r1, = 1024 3、内存访问指令 ldr、str、ldm、
4、stm ldr 既可以指低至读取伪指令,也可以是内存访问指令。当他的第二个参数前面有=时标 伪指令,否则表内存访问指令。 ldr 指令从内存中读取数据到寄存器,str 指令把寄存器的指存储到内存中,他们的操作数 都是 32 位的。 ldr r1, r2, #4 ldr r1,r2 ldr r1,r2, #4 str r1 ,r2, #4 str r1, r2 str r1, r2,#4 寄存器传送指令可以用一条指令将 16 个可见寄存器(R0R15)的任意子集合(或全部)存 储到存储器或从存储器中读取数据到该寄存器集合中。 与单寄存器存取指令相比, 多寄存器 数据存取可用的寻址模式更加有限。多
5、寄存器存取指令的汇编格式如下: LDM/STMRn!, 4、加减指令 add、sub add r1, r2, #1 sub r1, r2, #1 5、程序状态寄存器的访问指令 msr,mrs ARM 指令中有两条指令,用于在状态寄存器和通用寄存器之间传送数据。修改状态寄存器一 般是通过“读取修改写回”三个步骤的操作来实现的。这两条指令分别是: 状态寄存器到通用寄存器的传送指令(MRS) 通用寄存器到状态寄存器的传送指令(MSR) 其汇编格式如下: MRS Rd,CPSR|SPSR 其汇编格式如下: MSR CPSR_f | SPSR_f,# MSR CPSR_ | SPSR_,Rm msr c
6、psr, r0 mrs r0, cpsr 6、异常中断指令 异常中断指令可以分为一下两种: 软件中断指令(SWI) 断点指令(BKPT仅用于 v5T 体系) 软件中断指令 SWI 用于产生 SWI 异常中断, 用来实现在用户模式下对操作系统中特权模式的 程序的调用;断点中断指令 BKPT 主要用于产生软件断点,供调试程序用。 7、其他伪指令 .extern main .text .global _start _start: .extern 定义一个外部符号(可以是变量也可以是函数),上面的代码表示表文本文件中 引用的 main 是一个外部函数。 .text表示下面的语句都属于代码段 .glob
7、al将本文件中的某个程序标号定义为全局的,如_start就是个全局函数 MRS (读状态寄存器)MRS r1, CPSR;CPSR-r1 MSR (写状态寄存器) MSR cpsr_c, #0xD3 ;CPSR7.0 = 0xD3 STMFD SP! R8-R9 含义:(1)SP=SP-4 字节 (2) R9-SP(3)SP=SP-4(4) R8SP LDMFD SP! R8-R9,PC 含义: (1)SPR8(2)SP=SP+4(3)SPR9(4)SP=SP+4(5)SPPC(6) SP=SP+4 ldmia sp! r0-r7pc 表示将 spsrspsr 的值赋给 cpsrcpsr B
8、lable跳转指令PC LDR 指令用于从存储器中将一个 32 位的字数据传送到目的寄存器中。 该指令通常用于从存 储器中读取 32 位的字数据到通用寄存器, 然后对数据进行处理。 当程序计数器 PC 作为目 的寄存器时, 指令从存储器中读取的字数据被当作目的地址, 从而可以实现程序流程的跳转。 指令示例: LDRR0,R1;将存储器地址为 R1 的字数据读入寄存器 R0。 LDRR0,R1,R2;将存储器地址为 R1+R2 的字数据读入寄存器 R0。 LDRR0,R1,8;将存储器地址为 R1+8 的字数据读入寄存器 R0。 LDRR0,R1,R2 ! ;将存储器地址为 R1+R2 的字数据
9、读入寄存器 R0,并将新地址 R1 R2 写入 R1 LDRR0,R1,8 ! ;将存储器地址为 R1+8 的字数据读入寄存器 R0,并将新地址 R1 8 写入 R1。 LDRR0,R1,R2;将存储器地址为 R1 的字数据读入寄存器 R0,并将新地址 R1 R2 写入 R1。 LDRR0,R1,R2,LSL2!;将存储器地址为 R1R24 的字数据读入寄存器 R0, 并将新地址 R1R24 写入 R1。 LDRR0,R1,R2,LSL2;将存储器地址为 R1 的字数据读入寄存器 R0,并 将新地址 R1R24 写入 R1。 (7)STR 指令的格式为: STR条件 源寄存器, STR 指令用
10、于从源寄存器中将一个 32 位的字数据传送到存储器中。与 LDR 对应 (8)采用多寄存器寻址方式,一条指令可以完成多个寄存器值的传送。这种寻址方式可以 用一条指令完成传送最多 16 个通用寄存器的值。以下指令: LDMIAR0,R1,R2,R3,R4;R1R0 ;R2R0 4 ; R3R08 ;R4R0 12 该指令的后缀 IA 表示在每次执行完加载/存储操作后,R0 按字长度增加,因此,指令可将 连续存储单元的值传送到 R1R4。 (9)SBC 指令的格式为: SBC条件S 目的寄存器,操作数 1,操作数 2 SBC 指令用于把操作数 1 减去操作数 2,再减去 CPSR 中的 C 条件标
11、志位的反码,并将结果 存放到目的寄存器中。操作数 1 应是一个寄存器,操作数 2 可以是一个寄存器,被移位的寄 存器,或一个立即数。该指令使用进位标志来表示借位,这样就可以做大于 32 位的减法。 注意不要忘记设置 S 后缀来更改进位标志。该指令可用于有符号数或无符号数的减法运算。 指令示例: SUBSR0,R1,R2; R0 = R1 - R2 - !C,并根据结果设置 CPSR 的进位标志 位 (10)BX带状态切换的跳转指令 (11)MCR 指令的格式为: MCR条件 协处理器编码,协处理器操作码 1,源寄存器,目的寄存器 1,目的寄存器 2, 协处理器操作码 2 MCR 指令用于将 A
12、RM 处理器寄存器中的数据传送到协处理器寄存器中,若协处理器不能成 功完成操作, 则产生未定义指令异常。 其中协处理器操作码 1 和协处理器操作码 2 为协处理 器将要执行的操作,源寄存器为 ARM 处理器的寄存器,目的寄存器 1 和目的寄存器 2 均为 协处理器的寄存器。 指令示例: MCRP3,3,R0,C4,C5,6;该指令将 ARM 处理器寄存器 R0 中的数据传送到 协处理器 P3 的寄存器 C4 和 C5 中。 (12)CMP 指令的格式为: CMP条件 操作数 1,操作数 2 CMP 指令用于把一个寄存器的内容和另一个寄存器的内容或立即数进行比较,同时更新 CPSR 中条件标志位
13、的值。该指令进行一次减法运算,但不存储结果,只更改条件标志位。 标志位表示的是操作数 1 与操作数 2 的关系(大、小、相等),例如,当操作数 1 大于操 作操作数 2,则此后的有 GT 后缀的指令将可以执行。 指令示例: CMP R1,R0;将寄存器 R1 的值与寄存器 R0 的值相减,并根据结果设置 CPSR 的标志位 CMP R1,100 ;将寄存器 R1 的值与立即数 100 相减,并根据结果设置 CPSR 的标志位 (13)批量数据加载/存储指令 LDM(或 STM)指令的格式为: LDM(或 STM)条件类型 基址寄存器!,寄存器列表 LDM(或 STM)指令用于从由基址寄存器所指
14、示的一片连续存储器到寄存器列表所指示的多 个寄存器之间传送数据, 该指令的常见用途是将多个寄存器的内容入栈 (SDM) 或出栈(LDM)。 其中,类型为以下几种情况: IA每次传送后地址加 1; IB每次传送前地址加 1; DA每次传送后地址减 1; DB每次传送前地址减 1; FD满递减堆栈; ED空递减堆栈; FA满递增堆栈; EA空递增堆栈; !为可选后缀,若选用该后缀,则当数据传送完毕之后,将最后的地址写入基址寄存器, 否则基址寄存器的内容不改变。 STMFDR13!,R0,R4-R12,LR;将寄存器列表中的寄存器(R0,R4 到 R12,LR) 存入堆栈 LDMFDR13!,R0,
15、R4-R12,PC ;将堆栈内容恢复到寄存器(R0,R4 到 R12,LR) (14)ORR 指令的格式为: ORR条件S 目的寄存器,操作数 1,操作数 2 ORR 指令用于在两个操作数上进行逻辑或运算,并把结果放置到目的寄存器中。操作数 1 应是一个寄存器,操作数 2 可以是一个寄存器,被移位的寄存器,或一个立即数。该指令 常用于设置操作数 1 的某些位。 指令示例: ORRR0,R0,3; 该指令设置 R0 的 0、1 位,其余位 保持不变。 (15)BIC 指令的格式为: BIC条件S 目的寄存器,操作数 1,操作数 2 BIC 指令用于清除操作数 1 的某些位,并把结果放置到目的寄存器中。操作数 1 应是一个 寄存器, 操作数 2 可以是一个寄存器, 被移位的寄存器, 或一个立即数。 操作数 2 为 32 位 的掩码,如果在掩码中设置了某一位,则清除这一位。未设置的掩码位保持不变。 指令示例: BICR0,R0,1011; 该指令清除 R0 中的位 0、1、和 3,其余的位 保持不变。 (16) ADR(小范围的地址读取伪指令) ADRL(中等范围的地址读取伪指令) LDR(大范围的地址读取伪指令) ldrr0, =0xFFFFC000 用于将基于 PC 的地址或基于寄存器的地址读取到寄存器中。 /伪指令通过汇编编译器替换成对应的 ARM/Thumb 指令。