【嵌入式系统】课程复习资料整理

news2024/12/26 10:50:14

【嵌入式系统】课程复习资料整理

一、绪论

1.定义

  • 从技术的角度定义:以应用为中心、以计算机技术为基础、软件硬件可裁剪、对功能、可靠性、成本、体积、功耗严格要求的专用计算机系统。
  • 从系统的角度定义:嵌入式系统是设计完成复杂功能的硬件和软件,并使其紧密耦合在一起的计算机系统。
  • 术语嵌入式反映了这些系统通常是更大系统中的一个完整的部分,称为嵌入的系统。嵌入的系统中可以共存多个嵌入式系统。

2.嵌入式系统的特点

  • 嵌入式系统中运行的任务是专用而确定
  • 嵌入式系统往往对实时性提出较高的要求,嵌入式系统中使用的操作系统一般是实时操作系统
  • 嵌入式系统运行需要高可靠性保障,比桌面系统的故障容忍能力弱很多
  • 嵌入式系统需要忍受长时间、无人值守条件下的运行
  • 嵌入式系统运行的环境恶劣
  • 嵌入式系统大都有功耗约束
  • 嵌入式系统比桌面通用系统可用资源少得多,为降低系统成本,降低功耗,嵌入式系统的资源配置遵循够用就行
  • 嵌入式系统的开发需要专用工具和特殊方法

3.嵌入式系统结构

  • 嵌入式系统一般由嵌入式微处理器、外围硬件设备、嵌入式操作系统(可选),以及用户的应用软件系统等四个部分组成
  • 哈佛结构:指令和数据有各自的总线,执行效率高,设计复杂度高
  • 冯诺依曼结构:存储程序原理,代码本身也是数据;简化了结构,降低了复杂性,总线的吞吐量成为性能提升的瓶颈

4.CISC(复杂指令集计算机)和RISC(精简指令集计算机)的特点

CISC(Complex Instruction Set Computer)复杂指令集计算机:

  • 指令集复杂:CISC指令集具有复杂的指令,每个指令可以执行多个操作,包括访问内存、算术运算、逻辑运算等,这些指令通常需要多个时钟周期来完成。
  • 少量通用寄存器:CISC架构通常包含少量通用寄存器
  • 面向内存:CISC架构通常设计为面向内存,每个指令能够直接访问内存,不需要中间变量,可以更快地执行操作。
  • 程序大小较小:由于CISC指令集具有复杂的指令,所以程序的大小相对较小,因为可以使用少量的指令来完成复杂的操作。

RISC(Reduced Instruction Set Computer)精简指令集计算机:

  • 指令集精简:RISC指令集具有精简的指令,每个指令只能执行一个操作,通常只需要一个时钟周期就能完成。指令规整、对称、简单。指令小于100条,基本寻址方式有2~3种;指令字长度一致,单拍完成,便于流水操作;
  • 大量通用寄存器:RISC架构通常只包含大量的通用寄存器
  • 面向寄存器:RISC架构通常设计为面向寄存器,每个指令都需要中间变量,使得指令执行速度更快。
  • 程序大小较大:由于RISC指令集具有精简的指令,所以程序的大小相对较大,需要使用更多的指令来完成复杂的操作。

5.嵌入式微处理器

  • ARM:体积小、低功耗、低成本、高性能
  • MIPS:无内部互锁流水级的微处理器,是一种处理器内核标准,基于RISC架构
  • PowerPC:基于RISC架构

6.使用实时操作系统主要有以下几个因素

  • 提高了系统的可靠性
  • 提高了开发效率,缩短了开发周期
  • 充分发挥了32位CPU的多任务潜力

7.嵌入式实时操作系统的优缺点

优点:

  • 在嵌入式实时操作系统环境下开发实时应用程序使程序的设计和扩展变得容易,不需要大的改动就可以增加新的功能。
  • 通过将应用程序分割成若干独立的任务模块,使应用程序的设计过程大为简化;而且对实时性要求苛刻的事件都得到了快速、可靠的处理。
  • 通过有效的系统服务,嵌入式实时操作系统使得系统资源得到更好的利用

缺点:

  • 需要额外的ROM/RAM开销,2~5%的CPU额外负荷。

8.嵌入式操作系统

  • uClinux
  • Windows CE
  • Android
  • iOS
  • VxWorks
  • μC/OS-II
  • eCos

二、ARM体系结构

1.IP核分类(根据IP核的提供方式分类)

  • 软核:综合之前的RTL代码,只经过功能仿真,需要经过综合以及布局布线才能使用。
  • 固核:完成软核的设计外,及门级电路综合和时序仿真等设计环节,以门级电路网表的形式提供给用户。
  • 硬核:基于物理描述并经过工艺验证,提供给用户的形式是电路物理结构、掩模版图和全套工艺文件。

2.ARM微处理器特点

  • 体积小、低功耗、低成本、高性能
  • 支持Thumb(16位)/ARM(32位)双指令集
  • 使用寄存器,指令执行速度更快
  • 大多数数据操作都在寄存器中完成
  • 寻址方式灵活简单,执行效率高
  • 指令长度固定

3.ARM系列产品表示(以ARM 926EJ-S为例)

  • 9表示Family number,7:ARM7、9:ARM9、10:ARM10、11:ARM11
  • 2表示Memory system,2:Cache+MMU、4: Cache + MPU、 6: no cache,MMU/MPU
  • 6表示Memory size,0: Cache size (4-128KB) 、6: TCM:Tightly Coupled Memory,紧耦合内存
  • EJ表示Extensions ,E: DSP extension、 J: Jazelle extension 、T: Thumb support
  • S表示Synthesizable

4.ARM7TDMI各字母含义(ARM7TDMI 之后的所有 ARM 内核,即使没有包含 “TDMI” 字符,也都默认包含了 TDMI 的功能特性)

  • T:支持Thumb指令集
  • D:片上调试,一个边界扫描链 JTAG,可使 CPU 进入调试模式
  • M:快速乘法器,32位乘32位得到64位,32位的乘加得到64位
  • I:Embedded ICE,嵌入式跟踪宏单元,用于实现断点观测及变量观测的逻辑电路部分。提供片上断点和调试点
  • E:DSP指令,增加了DSP算法处理器指令:16位乘加指令,饱和的带符号数的加减法,双字数据操作,cache预取指令
  • J:Java加速器Jazelle,提高java代码的运行速度
  • S:可综合,提供VHDL或Verilog语言设计文件

5.AMBA总线体系结构(ARM微控制器使用的是AMBA总线体系结构)

  • AHB总线(Advanced High-performance Bus):用于连接高性能系统模块。它支持突发数据传输方式及单个数据传输方式,所有时序参考同一个时钟沿。
  • ASB总线(Advanced System Bus):用于连接高性能系统模块,在不必要使用AHB的高速特性的场合,它支持突发数据传输模式。
  • APB总线(Advance Peripheral Bus):是一个简单接口支持低性能的外围接口。
  • 3.0 引入AXI总线 (Advanced eXtensible Interface)

6.ARM7系列采用三级流水线

  • 第一级取指:取指级的任务是从程序存储器中读取指令。
  • 第二级译码:译码级完成对指令的解析,并为下一个周期准备数据路径需要的控制信号。由指令与译码逻辑完成,不占用数据通路。
  • 第三级执行:执行完成指令要求的操作,并根据需要将结果写回目的寄存器。

7.ARM7单周期指令最佳流水线

在这里插入图片描述

8.ARM9具有5级流水线
在这里插入图片描述

9.ARM处理器有37(31+6)个物理寄存器,31个通用寄存器和6个状态寄存器

10.ARM指令集

ARM指令集可分为5大类指令,所有指令都可以条件执行,其中一些指令还可以根据执行结果更新CPSR寄存器的相关标志位.

  • 数据处理指令:MOV, AND, SUB,ADD
  • 加载和存储指令: LDR,STR,LDM,STM
  • 分支指令: B, BX
  • 协处理器指令: LDC, STC
  • 杂项指令: SWI, MRS,MSR

11.Thumb指令集

16位Thumb指令集:是ARM指令集的子集,按16位指令重新编码,固定的16位指令

  • 分支指令;
  • 数据处理指令;
  • 寄存器加载和存储指令;
  • 异常产生指令。

12.ARM体系结构中的数据类型

  • 字节(Byte):在ARM体系结构和8位/16位处理器体系结构中,字节的长度均为8位。
  • 字(Word):在ARM体系结构中,字的长度为32位,必须分配为占用4个字节。
  • 半字(Half-Word):在ARM体系结构中,半字的长度为16位,必须分配为占用两个字节。

13.ARM微处理器的工作状态

  • ARM状态—处理器执行32位的字对齐的ARM指令,伪指令CODE32声明;
  • Thumb状态—处理器执行16位的、半字对齐的Thumb指令,伪指令CODE16声明。

14.处理器状态切换

  • 进入Thumb状态:当操作数寄存器的状态位==(位[0])为1时,执行BX(带状态切换分支指令)==进入Thumb状态。如果处理器在Thumb状态进入异常,则当异常处理返回时,自动转换到Thumb状态。
  • 进入ARM状态:当操作数寄存器的状态位==(位[0])为0==时执行BX指令进入ARM状态。当处理器进行异常处理时,进入ARM状态,从异常向量地址处开始执行。

15.ARM体系结构的存储器格式

  • ==大端格式(Big Endian)==字数据的高字节存储在低地址中,而字数据的低字节则存放在高地址中。
  • ==小端格式(Little Endian)==低地址中存放的是字数据的低字节,高地址存放的是字数据的高字节。
  • ARM默认小端格式,但用户可设置大、小端格式

16.处理器模式

处理器模式说明备注
用户(usr)正常程序工作模式不能直接切换到其它模式
系统(sys)用于支持操作系统的特权任务等与用户模式类似,但具有可以直接切换到其他模式等特权
快中断(fiq)支持高速数据传输及通道处理FIQ异常响应时进入此模式
中断(irq)用于通用中断处理IRQ异常响应时进入此模式
管理(svc)操作系统保护代码系统复位和软件中断响应时进入此模式
中止(abt)用于支持虚拟内存和/或存储器保护预取中止和数据中止
未定义(und)支持硬件协处理器的软件仿真未定义指令异常响应时进入此模式
  • 除用户模式外,其他模式均为特权模式;特权模式可以自由地切换处理器模式,而用户模式不能直接切换到别的模式。
  • 除用户模式和系统模式外,其它模式均为异常模式。它们除了可以通过程序切换进入外,也可以由特定的异常进入。
  • 用户模式和系统模式使用完全相同的寄存器

17.寄存器组织

  • ARM处理器有共37个寄存器,分成两大类:31个通用32位寄存器;6个状态寄存器。
  • 寄存器R0~R13为保存数据或地址值的通用寄存器。
  • R0~R7为未分组的寄存器,也就是说对于任何处理器模式,这些寄存器都对应于相同的32位物理寄存器。
  • 寄存器R8~R14为分组寄存器。它们所对应的物理寄存器取决于当前的处理器模式,几乎所有允许使用通用寄存器的指令都允许使用分组寄存器
  • 寄存器R13常作为堆栈指针(SP)
  • R14为链接寄存器(LR),在结构上有两个特殊功能:
    • 在每种模式下,模式自身的R14版本用于保存子程序返回地址;
    • 当发生异常时,该模式下的R14被设置成该异常模式将要返回的地址。
  • 寄存器R15为程序计数器(PC),它指向正在取指的地址。
    • 正常操作时,从R15读取的值是处理器正在取指的地址,即当前正在执行指令的地址加上8个字节(两条ARM指令的长度)。
    • 由于ARM指令总是以字为单位,所以R15寄存器的最低两位总是为0。
    • 当使用STR或STM指令保存R15时,会有一个例外:这些指令可能将当前指令地址加8字节或加12字节保存(将来可能还有其它数字)。偏移量是8还是12取决于具体的ARM芯片
  • 寄存器CPSR为程序状态寄存器;每种异常都有自己的SPSR,在因为异常事件而进入异常时它保存CPSR的当前值,异常退出时可通过它恢复CPSR。
  • Thumb状态下的寄存器集是ARM状态集的子集,程序员可以直接访问的寄存器为:8个通用寄存器R0~R7;程序计数器(PC);堆栈指针(SP);链接寄存器(LR);有条件访问程序状态寄存器( CPSR)。
  • 在发生异常时,处理器自动进入ARM状态。
  • 在Thumb状态中,高寄存器(R8~R12)不是标准寄存器集的一部分。汇编语言程序员对它们的访问受到限制,但可以将它们用于快速暂存。只能使用MOV、CMP和ADD指令对高寄存器操作。
  • CPSR反映了当前处理器的状态:4个条件码标志;2个中断控制位; 5个对当前处理器模式进行编码的位;1个指示当前执行指令的工作状态位;保留位

18.程序状态寄存器

在这里插入图片描述

  • 保留位被保留将来使用。为了提高程序的可移植性,当改变CPSR标志和控制位时,请不要改变这些保留位。另外,请确保您程序的运行不受保留位的值影响,因为将来的处理器可能会将这些位设置为1或者0。
  • 最低8位为控制位,当发生异常时,这些位被硬件改变。当处理器处于一个特权模式时,可用软件操作这些位。
  • 当进行加法运算,并且发生有符号溢出时V=1,否则V=0,其它指令V通常不变。
  • 当进行加法运算,并且最高位产生进位时C=1,否则C=0。当进行减法运算,并且最高位产生借位时C=1,否则C=0。对于移位操作指令,C为从最高位最后移出的值,其它指令C通常不变;
  • 指令结果为0时Z=1(表示比较结果“相等”),否则Z=0
  • 运算结果的最高位反映在该标志位。对于有符号二进制补码,结果为负数时N=1,结果为正数或零时N=0;
  • 大多数“数值处理指令”可以选择是否影响条件代码标志位(指令带S后缀);但有些指令执行总是影响条件代码标志。 所有ARM指令都可按条件来执行,而Thumb指令中只有分支指令可按条件执行。

19.CPSR模式位设置表

M[4:0]模式
10000用户
10001快中断
10010中断
10011管理
10111中止
11011未定义
11111系统

20.状态寄存器访问指令MRS,MSR

  • MRS: 状态寄存器到通用寄存器的传送指令(读状态寄存器)
  • MSR: 通用寄存器到状态寄存器的传送指令(写状态寄存器)
  • MRS和MSR指令可以实现对状态寄存器的读、修改、写操作,即修改状态寄存器的值。

21.异常处理器模式

异常类型模式向量地址
复位管理0x00000000
未定义指令未定义0x00000004
软件中断(SWI)管理0x00000008
预取中止(取指令存储器中止)中止0x0000000C
数据中止(数据访问存储器中止)中止0x00000010
IRQ(中断)IRQ0x00000018
FIQ(快速中断)FIQ0x0000001C

22.异常优先级

异常类型优先级
复位1(最高优先级)
数据中止2
FIQ3
IRQ4
预取中止5
未定义指令6
SWI6(最低优先级)

23.异常注意

  • 中断返回指令的寄存器列表(其中必须包括PC)后的“^”符号表示这是一条特殊形式的指令。这条指令在从存储器中装载PC的同时(PC是最后恢复的),CPSR也得到恢复。
  • 使用的堆栈指针SP(R13)是属于异常模式的寄存器,每个异常模式有自己的堆栈指针。如R13_irq
  • 堆栈指针应必须在系统启动时初始化。

24.进入异常

  • 1.在适当的LR中保存下一条指令的地址(R14_irq),当异常入口来自:

    • ARM状态,那么ARM7TDMI将当前指令地址加4或加8复制(取决于异常的类型)到LR中;
    • 为Thumb状态,那么ARM7TDMI将当前指令地址加4或加8 (取决于异常的类型)复制到LR中。
  • 2.将CPSR复制到适当的SPSR(如SPSR_irq)中;

  • 3.将CPSR模式位强制设置为与异常类型相对应的值;

  • 4.强制PC从相关的异常向量处取指。

25.异常处理

  • ARM7TDMI内核在中断异常时置位中断禁止标志(CPSR 第I位赋值=0x1),这样可以防止不受控制的异常嵌套
  • 异常总是在ARM状态中进行处理。当处理器处于Thumb状态时发生了异常,在异常向量地址装入PC时,会自动切换到ARM状态。
  • 除了复位异常外,其余的异常都需要返回
  • 当异常结束时,异常处理程序必须:
    • 1.将LR(如R14_irq)中的值减去偏移量后存入PC,偏移量根据异常的类型而有所不同;
    • 2.将SPSR(如SPSR_irq)的值复制回CPSR;
    • 3.若在进入异常处理时设置了中断禁止标志(I/F位)则清零该标志。
  • 无论发生什么异常(除复位),内核总是会首先将 PC-4 放到LR寄存器中。

25.软件中断指令(SWI)

  • 使用软件中断(SWI)指令可以进入管理模式,通常用于请求一个特定的管理函数。
  • SWI处理程序通过执行下面的指令返回:MOVS PC,R14_svc 这个动作恢复了PC和CPSR并返回到SWI之后的指令
  • PC未更新

26.未定义的指令(UND)

  • 当ARM7TDMI处理器遇到一条自己和系统内任何协处理器都无法处理的指令时,ARM7TDMI内核执行未定义指令异常程序
  • 软件可使用这一机制通过模拟未定义的协处理器指令来扩展ARM指令集。
  • 在模拟处理了失败的指令后,陷阱程序执行下面的指令:MOVS PC,R14_und 这个动作恢复了PC和CPSR并返回到未定义指令之后的指令。
  • PC未更新

27.快速中断请求(FIQ)

  • 快速中断请求(FIQ)适用于对一个突发事件的快速响应,这得益于在ARM状态中,快中断模式有8个专用的寄存器可用来满足寄存器保护的需要(这可以加速上下文切换的速度)。
  • 不管异常入口是来自ARM状态还是Thumb状态,FIQ处理程序都会通过执行下面的指令从中断返回:SUBS PC,R14_fiq,#4
  • 在一个特权模式中,可以通过置位CPSR中的F位来禁止FIQ异常。
  • PC已更新

28.中断请求(IRQ)

  • 中断请求(IRQ)异常是一个由nIRQ输入端的低电平所产生的正常中断(在具体的芯片中,nIRQ由片内外设拉低,nIRQ是内核的一个信号,对用户不可见)。
  • IRQ的优先级低于FIQ。进入FIQ处理时FIQ和IRQ都被禁。在一个特权模式下,可通过置位CPSR中的I 位来禁止IRQ。
  • 不管异常入口是来自ARM状态还是Thumb状态,FIQ处理程序都会通过执行下面的指令从中断返回:SUBS PC,R14_irq,#4
  • PC已更新

29.FIQ为什么比IRQ快呢?

  • FIQ比IRQ有更高优先级,如果FIQ和IRQ同时产生,那么FIQ先处理
  • ARM的FIQ模式提供了更多的banked寄存器,R8,R9,R10,R11,R12,模式切换时CPU自动保存这些值到banked寄存器,退出FIQ模式时自动恢复
  • FIQ的中断向量地址在0x0000001C,而IRQ的在0x00000018。这样可以直接在1C处放FIQ的中断处理程序,不需要跳转,所以响应速度快。
  • IRQ和FIQ的中断响应延迟有区别,IRQ的响应并不及时,从Verilog仿真来看,IRQ会延迟几个指令周期才跳转到中断向量处

30.中止(ABT)

  • 中止发生在对存储器的访问不能完成时,当出现异常后,要重新再执行一次这条指令,中止包含两种类型:
    • 预取中止: 发生在指令预取过程中
    • 数据中止: 发生在对数据访问时

31.预取中止

  • 当发生预取中止时,ARM7TDMI内核将预取的指令标记为无效,但在指令到达流水线的执行阶段时才进入异常
  • 如果指令在流水线中因为发生分支而没有被执行,中止将不会发生
  • 在处理中止的原因之后,不管处于哪种处理器操作状态,处理程序都会执行下面的指令恢复PC和CPSR并重试被中止的指令: SUBS PC,R14_abt,#4
  • PC未更新

32.数据中止

  • 在修复产生中止的原因后,不管处于哪种处理器操作状态,处理程序都必须执行下面的返回指令,这个动作恢复了PC和CPSR并重试被中止的指令: SUBS PC,R14_abt,#8
  • PC已更新

三、ARM指令集

1.ARM指令概述

  • ARM微处理器是基于精简指令计算机==(RISC)==的原理设计的,指令集和相关译码机制比较简单。
  • ARM7系列微处理器具有32位的ARM指令集和16位的Thumb指令集
  • ARM指令集效率高,但是代码密度低,占用较大的内存空间;
  • Thumb指令集属于ARM指令集的子集,具有较好的代码密度,功能简单。
  • 所有的ARM指令都是有条件执行
  • 而Thumb指令集只有一条指令(B)具有条件执行的功能
  • ARM指令和Thumb指令可以相互调用,两者之间的状态切换所用的开销几乎为0。

2.ARM处理器寻址方式

ARM处理器具有9种基本寻址方式。

  • (1) 寄存器寻址
  • (2) 立即寻址
  • (3) 寄存器移位寻址
  • (4) 寄存器间接寻址
  • (5)== 基址寻址==
  • (6) 多寄存器寻址
  • (7) 堆栈寻址
  • (8) 块拷贝寻址
  • (9) 相对寻址

3.寄存器寻址

  • 操作数的值在寄存器中,指令中的地址码字段指出的是寄存器编号,指令执行时直接取出寄存器值来操作。
  • 寄存器寻址指令举例如下:
    • MOV R1,R2 ;将R2的值存入R1
    • SUB R0,R1,R2 ;将R1的值减去R2的值,结果保存到R0

4.立即寻址

  • 立即寻址指令中的操作码字段后面的地址码部分即是操作数本身,也就是说,数据就包含在指令当中,取出指令也就取出了可以立即使用的操作数(这样的数称为立即数)。
  • 立即寻址指令举例如下:
    • SUBS R0,R0,#1 ;R0减1,结果放入R0,并且影响标志位
    • MOV R0,#0xFF000 ;将立即数0xFF000装入R0寄存器

5.寄存器移位寻址

  • 寄存器移位寻址是ARM指令集特有的寻址方式。当第2个操作数是寄存器移位方式时,第2个寄存器操作数在与第1个操作数结合之前,选择进行移位操作。
  • 寄存器移位寻址指令举例如下:
    • MOV R0,R2,LSL #3 ;R2的值左移3位,结果放入R0,即是R0=R2×8
    • ANDS R1,R1,R2,LSL R3 ;R2的值左移R3位,然后和R1相 “与”操作,结果放入R1

6.寄存器间接寻址

  • 寄存器间接寻址指令中的地址码给出的是一个通用寄存器的编号,所需的操作数保存在寄存器指定地址的存储单元中,即寄存器为操作数的地址指针。
  • 寄存器间接寻址指令举例如下:
    • LDR R1,[R2] ;将R2指向的存储单元的数据读出保存在R1中
    • STR R1,[R0]

7.基址寻址

  • 基址寻址就是将基址寄存器的内容与指令中给出的偏移量相加,形成操作数的有效地址。
  • 基址寻址指令举例如下:
    • LDR R2,[R3,#0x0C] ;读取R3+0x0C地址上的存储单元的内容,放入R2
    • STR R1,[R0,#-4]! ;先R0-4,然后把R1的值保存到R0-4指定的存储单元

8.多寄存器寻址

  • 多寄存器寻址一次可传送几个寄存器值,允许一条指令传送16个寄存器的任何子集或所有寄存器。
  • 多寄存器寻址指令举例如下:
    • LDMIA R1!,{R2-R7,R12} ;将R1指向的单元中的数据读出到R2~R7、R12中(R1自动加4)
    • STMIA R0!,{R2-R7,R12} ;将寄存器R2~R7、R12的值保存到R0指向的存储; 单元中(R0自动加4)
  • 使用多寄存器寻址指令时,寄存器子集的顺序是按由小到大的顺序排列,连续的寄存器可用“-”连接;否则用“,”分隔书写。

9.堆栈寻址

  • 堆栈是一个按特定顺序进行存取的存储区,操作顺序为==“后进先出”== 。
  • 堆栈寻址是隐含的,它使用一个专门的寄存器(堆栈指针)指向一块存储区域(堆栈),指针所指向的存储单元即是堆栈的栈顶
  • 存储器堆栈可分为两种:
  • 向上生长:向高地址方向生长,称为递增堆栈
  • 向下生长:向低地址方向生长,称为递减堆栈

10.块拷贝寻址

  • 块拷贝寻址方式使用多寄存器传送指令将数据块从存储器的某一位置拷贝到另一位置。
  • 如:
    • STMIA R0!,{R1-R7} ;将R1~R7的数据保存到存储器中。存储指针在保存第一个值之后增加,增长方向为向上增长。
    • STMIB R0!,{R1-R7} ;将R1~R7的数据保存到存储器中。存储指针在保存第一个值之前增加,增长方向为向上增长。
  • 常用的加载存储指令有:
    • LDM—批量数据加载指令;
    • STM—批量数据存储指令。
    • LDM(或STM)指令的格式为:LDM(或STM){条件}{类型} 基址寄存器{!},寄存器列表
  • {类型}为以下几种情况:
    • IA 每次传送后地址加4;
    • IB 每次传送前地址加4;
    • DA 每次传送后地址减4;
    • DB 每次传送前地址减4;
    • FD 满递减堆栈;
    • ED 空递减堆栈;
    • FA 满递增堆栈;
    • EA 空递增堆栈;
  • {!}为可选后缀,若选用该后缀,则当数据传送完毕之后,将最后的地址写入基址寄存器,否则基址寄存器的内容不改变

11.相对寻址

  • 相对寻址是基址寻址的一种变通。由程序计数器PC提供基准地址,指令中的地址码字段作为偏移量,两者相加后得到的地址即为操作数的有效地址
  • MOV PC,R14 ;返回

12.指令格式

  • <opcode> {<cond>} {S} <Rd> ,<Rn>{,<operand2>}
  • 其中<>号内的项是必须的,{ }号内的项是可选的。各项的说明如下:
    • opcode:指令助记符;
    • cond:执行条件;
    • S:是否影响CPSR寄存器的值;
    • Rd:目标寄存器;
    • Rn:第1个操作数的寄存器;
    • operand2:第2个操作数;
  • operand2有如下的形式:
    • #immed_8r ——常数表达式;
    • Rm ——寄存器方式;
    • Rm, shift ——寄存器移位方式;

13.ARM存储器访问指令

  • ARM处理器是典型的RISC处理器,对存储器的访问只能使用加载和存储指令实现
  • 冯•诺依曼存储结构,程序空间、RAM空间及I/O映射空间统一编址,除对RAM操作以外,对外围IO、程序数据的访问均要通过加载/存储指令进行。
  • 存储器访问指令分为单寄存器操作指令多寄存器操作指令

14.LDR和STR

  • LDR/STR指令寻址非常灵活,它由两部分组成,其中一部分为一个基址寄存器,可以为任一个通用寄存器;另一部分为一个地址偏移量。地址偏移量有以下3种格式
  • 立即数:立即数可以是一个无符号的数值。这个数据可以加到基址寄存器,也可以从基址寄存器中减去这个数值。
  • 寄存器:寄存器中的数值可以加到基址寄存器,也可以从基址寄存器中减去这个数值。
  • 寄存器及移位常数:寄存器移位后的值可以加到基址寄存器,也可以从基址寄存器中减去这个数值。
  • 从寻址方式的地址计算方法分,加载/存储指令有以下3种格式:
  • 零偏移: 如:LDR Rd,[Rn]
  • 前索引偏移(前变址):如:LDR Rd,[Rn,#0x04]!
  • 后索引偏移(后变址):如:LDR Rd,[Rn],#0x04
  • 有符号位半字/字节加载是指用符号位加载扩展到32位,无符号半字加载是指用零扩展到32位;
  • 地址对齐——半字读写的指定地址必须为偶数,否则将产生不可靠的结果。
  • LDM和STM的主要用途是现场保护、数据复制、常数传递等
  • 后缀“!”表示最后的地址写回到Rn中。

15.多寄存器存取

  • 模式说明模式说明
    IA每次传送后地址加4FD满递减堆栈
    IB每次传送前地址加4ED空递减堆栈
    DA每次传送后地址减4FA满递增堆栈
    DB每次传送前地址减4EA空递增堆栈
    数据块传送操作堆栈操作
  • 进行堆栈操作操作时,要先设置堆栈指针(SP),然后使用堆栈寻址指令STMFD/LDMFD 、STMED/LDMED、STMFA/LDMFA和STMEA/LDMEA实现堆栈操作。
  • 后缀“^”不允许在用户模式或系统模式下使用。
  • 若在LDM指令且寄存器列表中包含有PC时使用,那么除了正常的多寄存器传送外,将SPSR也拷贝到CPSR中,这可用于异常处理返回。
  • 使用后缀“^”进行数据传送且寄存器列表不包含PC时,加载/存储的是用户模式的寄存器,而不是当前异常模式的寄存器。

16.寄存器和存储器交换指令

  • SWP指令用于将一个内存单元(该单元地址放在寄存器Rn中)的内容读取到一个寄存器Rd中,同时将另一个寄存器Rm的内容写入到该内存单元中。
  • 指令格式如下:SWP{cond}{B} Rd,Rm,[Rn]
  • B为可选后缀,若有B,则交换字节,否则交换32位字;Rd用于保存从存储器中读入的数据;Rm的数据用于存储到存储器中,若Rm与Rd相同,则为寄存器与存储器内容进行交换;Rn为要进行数据交换的存储器地址,Rn不能与Rd和Rm相同。
  • SWP R1,R1,[R0] ;将R1的内容与R0指向的存储单元的内容进行交换
  • SWPB R1,R2,[R0] ;将R0指向的存储单元内的容读取一字节数据到R1中==(高24位清零),并将R2的内容写入到该内存单元中(最低字节有效)== ,只写R2的最低8位给内存

17.ARM数据处理指令

  • 数据处理指令大致可分为3类: 数据传送指令;算术逻辑运算指令;比较指令。
  • 数据处理指令只能对寄存器的内容进行操作,而不能对内存中的数据进行操作。
  • 所有ARM数据处理指令均可选择使用S后缀,并影响状态标志。
  • 比较指令CMP、CMN、TST和TEQ不需要后缀S,它们会直接影响状态标志。
  • MOV指令将立即数或寄存器传送到目标寄存器(Rd),可用于移位运算等操作。
  • MVN指令将立即数或寄存器(operand2)按位取反后传送到目标寄存器(Rd),因为其具有取反功能,所以可以装载范围更广的立即数。
  • 算术运算
    助记符说明操作条件码位置
    ADD Rd, Rn, operand2加法运算指令Rd←Rn+operand2ADD{cond}{S}
    SUB Rd, Rn, operand2减法运算指令Rd←Rn-operand2SUB{cond}{S}
    RSB Rd, Rn, operand2逆向减法指令Rd←operand2-RnRSB{cond}{S}
    ADC Rd, Rn, operand2带进位加法Rd←Rn+operand2+CarryADC{cond}{S}
    SBC Rd, Rn, operand2带进位减法指令Rd←Rn-operand2-(NOT)CarrySBC{cond}{S}
    RSC Rd, Rn, operand2带进位逆向减法指令Rd←operand2-Rn-(NOT)CarryRSC{cond}{S}
  • 逻辑运算指令
    助记符说明操作条件码位置
    AND Rd, Rn, operand2逻辑与操作指令Rd←Rn & operand2AND{cond}{S}
    ORR Rd, Rn, operand2逻辑或操作指令Rd←Rn | operand2ORR{cond}{S}
    EOR Rd, Rn, operand2逻辑异或操作指令Rd←Rn ^ operand2EOR{cond}{S}
    BIC Rd, Rn, operand2位清除指令Rd←Rn & (~operand2)BIC{cond}{S}
  • 比较指令
    助记符说明操作条件码位置
    CMP Rn, operand2比较指令标志N、Z、C、V ←Rn-operand2CMP{cond}
    CMN Rn, operand2负数比较指令标志N、Z、C、V←Rn+operand2CMN{cond}
    TST Rn, operand2位测试指令标志N、Z、C、V←Rn & operand2TST{cond}
    TEQ Rn, operand2相等测试指令标志N、Z、C、V←Rn ^ operand2TEQ{cond}
  • 乘法指令
助记符说明操作条件码位置
MUL Rd,Rm,Rs32位乘法指令Rd←Rm*Rs (Rd≠Rm)MUL{cond}{S}
MLA Rd,Rm,Rs,Rn32位乘加指令Rd←Rm*Rs+Rn (Rd≠Rm)MLA{cond}{S}
UMULL RdLo,RdHi,Rm,Rs64位无符号乘法指令(RdHi,RdLo) ←Rm*RsUMULL{cond}{S}
UMLAL RdLo,RdHi,Rm,Rs64位无符号乘加指令(RdHi,RdLo) ←Rm*Rs+(RdHi,RdLo)UMLAL{cond}{S}
SMULL RdLo,RdHi,Rm,Rs64位有符号乘法指令(RdHi,RdLo) ←Rm*RsSMULL{cond}{S}
SMLAL RdLo,RdHi,Rm,Rs64位有符号乘加指令(RdHi,RdLo) ←Rm*Rs+(RdHi,RdLo)SMLAL{cond}{S}
  • 分支指令
    • B指令,该指令跳转范围限制在当前指令的±32M字节地址内(ARM指令为字对齐,最低2位地址固定为0)。
    • BL指令适用于子程序调用,使用该指令后,下一条指令的地址被拷贝到R14(即LR) 中,然后跳转到指定地址运行程序。跳转范围限制在当前指令的±32M字节地址内。
    • BX指令,该指令可以根据跳转地址(Rm)的最低位来切换处理器状态,bit[0]=0为ARM状态,否则为Thumb状态。其跳转范围限制在当前指令的±32M字节地址内(ARM指令为字对齐,最低2位地址固定为0)。
      | 助记符 | 说明 | 操作 | 条件码位置 |
      | -------------- | ------------------------ | ---------------------------- | ------------ |
      | B label | 分支指令 | PC←label | B{cond} |
      | BL label | 带链接的分支指令 | LR←PC-4,PC←label | BL{cond} |
      | BX Rm | 带状态切换的分支指令 | PC←label,切换处理器状态 | BX{cond} |
  • 只有MRS指令可以对状态寄存器CPSR和SPSR进行操作。
  • 只有MSR指令可以对状态寄存器CPSR和SPSR进行操作
  • 只有在特权模式下才能修改状态寄存器。
  • 程序中不能通过MSR指令直接修改CPSR中的T控制位来实现ARM状态/Thumb状态的切换,必须使用BX指令完成处理器状态的切换(因为BX指令属分支指令,它会打断流水线状态,实现处理器状态切换)。

18.ARM伪指令

  • ARM伪指令有四条,分别为ADR伪指令、ADRL伪指令、LDR伪指令、NOP伪指令。
  • ADR伪指令,小范围的地址读取
  • ADRL伪指令,中等范围的地址读取
  • LDR伪指令,大范围的地址读取
  • NOP伪指令, 空操作伪指令

19.Thumb指令集

  • 在编写Thumb指令时,先要使用伪指令CODEl6声明,而且在ARM指令中要使用BX指令跳转到Thumb指令,以切换处理器状态。
  • 编写ARM指令时,则可使用伪指令CODE32声明。
  • 除了分支指令B有条件执行功能外,其它指令均为无条件执行。

20.Thumb指令集与ARM指令集的区别

  • 分支指令 程序相对转移,特别是条件跳转与ARM代码下的跳转相比,在范围上有更多的限制。
  • 数据处理指令
    • 数据处理操作比ARM状态的更少。
    • 访问寄存器R8~R15受到一定限制。
    • 除MOV和ADD指令访问R8~ R15外,其它数据处理指令总是更新CPSR中的ALU状态标志。
    • 访问寄存器R8~R15的Thumb数据处理指令不能更新CPSR中的ALU状态标志。
  • 单寄存器加载和存储指令 在Thumb状态下,单寄存器加载和存储指令只能访问寄存器R0~R7。
  • 多寄存器加载和存储指令
    • LDM和STM指令可以将任何范围为R0~R7的寄存器子集加载或存储,多寄存器加载和存储指令只有LDMIA和STMIA指令。
    • PUSH和POP指令使用堆栈指令R13作为基址实现满递减堆栈。
    • 除R0~R7外,PUSH指令还可以存储LR, 并且POP指令可以加载PC。

四、汇编程序设计

1.ARM伪操作

  • 在ARM的汇编程序中,有如下几种伪指令:符号定义伪指令、数据定义伪指令、汇编控制伪指令、宏指令以及其他伪指令。

2.符号定义伪指令

  • GBLA伪指令用于定义一个全局的数字变量,并初始化为0;
  • GBLL伪指令用于定义一个全局的逻辑变量,并初始化为F(假);
  • GBLS伪指令用于定义一个全局的字符串变量,并初始化为空;
  • 以上三条伪指令用于定义全局变量,因此在整个程序范围内变量名必须唯一。
  • LCLA伪指令用于定义一个局部的数字变量,并初始化为0;
  • LCLL伪指令用于定义一个局部的逻辑变量,并初始化为F(假);
  • LCLS伪指令用于定义一个局部的字符串变量,并初始化为空;
  • 以上三条伪指令用于声明局部变量,在其作用范围内变量名必须唯一。
  • SETA伪指令用于给一个数学变量赋值;
  • SETL伪指令用于给一个逻辑变量赋值;
  • SETS伪指令用于给一个字符串变量赋值;
  • 其中,变量名为已经定义过的全局变量或局部变量,表达式为将要赋给变量的值。
  • RLIST伪指令可用于对一个通用寄存器列表定义名称,使用该伪指令定义的名称可在ARM指令LDM/STM中使用。

3.数据定义(Data Definition)伪操作

  • DCB 用于分配一片连续的字节存储单元并用指定的数据初始化。
  • DCW(DCWU)用于分配一片连续的半字存储单元并用指定的数据初始化。
  • DCD(DCDU) 用于分配一片连续的字存储单元并用指定的数据初始化。
  • DCFD(DCFDU)用于为双精度的浮点数分配一片连续的字存储单元并用指定的数据初始化。
  • DCFS(DCFSU) 用于为单精度的浮点数分配一片连续的字存储单元并用指定的数据初始化。
  • DCQ(DCQU) 用于分配一片以8字节为单位的连续的存储单元并用指定的数据初始化。
  • DCDO 用于分配一段字的内存单元,将每个单元的内容初始化为该单元相对于基址寄存器的偏移量
  • DCI 用于分配一段字的内存单元,并用单精度的浮点数据初始化,指定内存单元存放的是代码,而不是数据
  • SPACE 用于分配一片连续的字节存储单元,并初始化为0
  • MAP 用于定义一个结构化的内存表首地址
  • FIELD 用于定义一个结构化的内存表的数据域
  • LTORG 用于声明一个文字池(缓冲池)

4.汇编控制

  • IF、ELSE、ENDIF条件汇编代码文件内的一段源代码
  • WHILE、WEND根据条件重复汇编
  • MACRO、MEND标识宏定义的开始和结束
  • MEXIT中途跳转出宏
  • AREA伪操作用于定义一个代码段或数据段
  • ALIGN伪操作可通过添加填充字节的方式,使当前位置满足一定的对齐方式。
  • ENTRY伪操作用于指定程序的入口点。在一个完整的汇编语言程序中至少要有一个ENTRY
  • END伪操作用于通知汇编器已经到了源程序的结尾。
  • EQU伪操作用于为程序中的常量、标号等定义一个等效的字符名称,类似于C语言中的#define。其中EQU可用“*”代替。
  • EXPORT伪操作用于在程序中声明一个全局的标号,该标号可在其他的文件中引用。EXPORT可用GLOBAL代替。标号在程序中区分大小写。
  • IMPORT伪操作用于通知编译器要使用的标号在其他的源文件中定义,但要在当前源文件中引用,
  • GET伪操作用于将一个源文件包含到当前的源文件中,并将被包含的源文件在当前位置进行汇编处理。
  • EXTERN伪操作用于通知编译器要使用的标号在其他的源文件中定义,但要在当前源文件中引用,如果当前源文件实际并未引用该标号,该标号就不会被加入到当前源文件的符号表中。
  • INCBIN伪操作用于将一个二进制目标代码文件或任意格式的数据文件包含到当前的源文件中,
  • RN 伪指令用于给一个寄存器定义一个别名。采用这种方式可以方便程序员记忆该寄存器的功能。其中,名称为给寄存器定义的别名,表达式为寄存器的编码。

5.数据比较跳转

  • CMP R5,#10 ;做减法
  • BEQ BRANCH1 ;如果R5为10,则跳转到BRANCH1
  • CMP R1,R2
  • ADDHI R1,R1,#1 ;如果R1>R2,则R1=R1+1
  • ADDLS R1,R1,#2 ;如果R1<=R2,则R1=R1+2……
  • ANDS R1,R1,#0x80 ;R1=R1&0x80,并设置相应的标志位
  • BNE WAIT ;如果R1的第7位0,则跳转到WAIT

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/499878.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Android多模块开发

Android多模块开发 1. 建立项目和多个模块 ​ app为主模块 ​ app-setting为功能模块&#xff0c;可作为独立模块运行&#xff0c;也可作为其他模块的资源模块 ​ app-video为功能模块 2. 建立公共环境文件(env.gradle)并在各模块配置 Step1&#xff1a; 建立在根目录下建…

第31步 机器学习分类实战:多轮建模

开始填坑之旅。 首先&#xff0c;之前提过&#xff0c;random_state这个参数&#xff0c;它的功能是确保每次随机抽样所得到的数据都是一样的&#xff0c;有利于数据的复现。比如&#xff0c;我们这十个ML模型&#xff0c;用的参数都是random_state666&#xff0c;这样作比较才…

【写一个hello的html页面,将页面放到服务器,通过浏览器访问页面,这个过程是怎么实现的?】第一个 servlet 程序

第一个 servlet 程序 第一个 servlet 程序1. 创建项目创建好后的 默认目录 解析 2. 引入依赖为什么要引入依赖&#xff1f; 3. 创建目录结构1、在 main 目录下创建一个 webapp 目录2、在 webapp 下创建一个 WEB-INF 目录3、在 WEB-INF 目录下创建一个 web.xml 文件4、web.xml 需…

章节3:02-Apache Commons Collections反序列化漏洞

章节3&#xff1a;02-Apache Commons Collections反序列化漏洞 02-Apache Commons Collections反序列化漏洞 漏洞爆出 2015.01.28 Gabriel Lawrence和Chris Frohoff https://speakerdeck.com/frohoff/appseccali-2015-marshalling-pickles-how-deserializing-objects-can-r…

《Java虚拟机学习》 asmtools 字节码汇编器使用 与 JVM识别方法重载 的思考

1.asmtools下载 链接&#xff1a;https://pan.baidu.com/s/1R3nAaUbN1Dkf6UKkdEMSEA?pwdk8l8 提取码&#xff1a;k8l8 2.结合方法重载实验的使用 总所周知&#xff0c;方法重载跟方法名无关&#xff0c;但对于JVM而言&#xff0c;区别方法主要通过 类名&#xff0c;方法名&…

java spring MVC REST风格概念叙述

REST属于spring MVC中的一个知识点 REST是三个单词的缩写 即 Representational State Transfer 意思为 表现形式状态转换 老实说 不用尝试字面上理解 因为字面意思 确实是比较抽象 其实 意思就是 访问网络资源的格式 转换 下图 对比了 传统风格和REST风格 请求路径的差别 RES…

【英语】大学英语CET考试,阅读部分2(长篇阅读,选词填空,综合演练)

文章目录 1、长篇阅读&#xff08;连连看&#xff0c;要会做&#xff09;1.1 解题技巧&#xff08;定位词扫读&#xff0c;看到大于看懂&#xff0c;一题带练&#xff09;1.2 做题方法复习总结1.3 题目练习&#xff08;2篇文章&#xff09; 2、选词填空&#xff08;只有5分&…

opencv_c++学习(五)

Mat类数值存储方式 上图为opencv中三通道数据的存储方式&#xff0c;反映到图像上则为空间维度为3*3&#xff0c;通道为3的图像。 Mat类的属性 Mat类的属性如上&#xff0c;在这里我们解释一下step。step是行列数与数据类型的字节数相乘的数据。 Mat类元素读取 在Mat中&…

云原生: istio+dapr构建多运行时服务网格...  多运行时是一个非常新的概念。在

2020 年&#xff0c;Bilgin Ibryam 提出了 Multi-Runtime&#xff08;多运行时&#xff09;的理念&#xff0c;对基于 Sidecar 模式的各种产品形态进行了实践总结和理论升华。那到底什么是多运行时呢&#xff1f;首先还是得从分布式应用的四大类基本需求讲起。简单来讲任何分布…

【力扣周赛】第344场周赛

【力扣周赛】第344场周赛 6416&#xff1a;找出不同元素数目差数组题目描述解题思路 6417&#xff1a;频率跟踪器题目描述解题思路 6418&#xff1a;有相同颜色的相邻元素数目题目描述解题思路 6419&#xff1a;使二叉树所有路径值相等的最小代价题目描述解题思路 6416&#xf…

C++ ---- 类和对象(上)

目录 本节目标 常见问题 面向过程和面向对象的理解 什么是类如何定义类 类的引入 类的定义 类的两种定义习惯 类的作用域 类的访问限定符 访问限定符介绍 封装 封装的意义 类的实例化 类对象模型 类对象的存储方式 结构体对齐 计算类对象的大小 this指针 问题…

数青蛙​、[USACO10FEB]Chocolate Giving S

一、1419. 数青蛙 思路 这道题有俩种解法&#xff0c;一是记数&#xff0c;二是贪心 记数&#xff1a; 这是官方的题解 我们用frog_ num来表示现在正在发出蛙鸣声的青蛙数目&#xff0c;用cnt[c] 示已经发出-次有效蛙鸣中的字符c的青蛙个数,比如当cnt[c] 2时表示当前有2只…

[mini LCTF 2023] 西电的部分

感觉比赛还是很不错&#xff0c;就是有点难了&#xff0c;不过都是简单题重复更没意思。作出一道来就有一点收获。 misc1 签到题也不简单&#xff0c;已经很久不作misc了&#xff0c;感觉这东西需要安的东西太多&#xff0c;怕机子累坏了。 一个复合的wav声音文件&#xff0…

【Android入门到项目实战-- 8.5】—— 使用HTTP协议访问网络的实践用法

目录 准备工作 一、创建HttpUtil类 二、调用使用 一个应用程序可能多次使用到网络功能&#xff0c;这样就会大量代码重复&#xff0c;通常情况下我们应该将这些通用的网络操作封装到一个类里&#xff0c;并提供一个静态方法&#xff0c;想要发送网络请求的时候&#xff0c;只…

【c语言】字符串匹配(搜索) | API仿真

c语言系列专栏&#xff1a;c语言之路重点知识整合 字符串知识点&#xff1a;字符串基本概念、存储原理 字符串匹配 目录 一、字符串匹配二、strstr仿真声明&#xff1a;指针方式定义&#xff1a;调用测试&#xff1a;运行结果&#xff1a; 一、字符串匹配 字符串匹配是对一个…

HttpClient连接池使用不当问题分析解决

目录 背景代码实现工具类功能实现模拟使用 问题分析与定位解决方案总结 背景 最近遇到一个HttpClient问题&#xff0c;某个接口一直报404错误。该接口使用HttpClient调用其他服务获取数据&#xff0c;为了提高接口调用性能&#xff0c;利用httpclient池化技术来保证请求的数量…

嵌入式中利用软件实现定时器的两种方法分析

目录 第一&#xff1a;简介 第二&#xff1a;链表实现方式 第三&#xff1a;结构体实现方式 第一&#xff1a;简介 在一般的嵌入式产品设计中&#xff0c;介于成本、功耗等&#xff0c;所选型的MCU基本都是资源受限的&#xff0c;而里面的定时器的数量更是有限。在我们软件…

Origin如何绘制基础图形?

文章目录 0.引言1.绘图操作2.图形设置3.图形标注 0.引言 因科研等多场景需要绘制专业的图表&#xff0c;笔者对Origin进行了学习&#xff0c;本文通过《Origin 2022科学绘图与数据》及其配套素材结合网上相关资料进行学习笔记总结&#xff0c;本文对绘制基础图形进行阐述。 1.…

2023.5.7 第五十二次周报

目录 前言 文献阅读&#xff1a;基于BO-EMD-LSTM模型预测教室长期二氧化碳浓度 背景 思路 BO-EMD-LSTM 混合模型 EMD 算法 与其他模型的比较 结论 论文代码 总结 前言 This week, I studied an article that uses LSTM to predict gas concentration.This study wa…

Springboot +Flowable,按角色分配任务

一.简介 在为 UserTask 设置处理人的时候&#xff0c;除了设置单个的处理人&#xff0c;也可以设置 Group&#xff08;分组&#xff09;&#xff0c;就是某一个用户组内的所有用户都可以处理该 Task。 二.绘制流程图 首先我们还是使用之前旧的流程图&#xff0c;流程图截图如…