嵌入式硬件DAY5(ARM汇编)

学习汇编的目的

ARM汇编的主要目的是为了编写ARM启动代码,启动代码启动以后,引导程序到c语言环境下运行。启动代码的主要任务有:

1.初始化异常向量表;

2.初始化各工作模式的栈指针寄存器

3.开启arm内核中断允许

4.将工作模式设置为user模式

5.引导程序进入C语言主函数执行

1.汇编代码格式(注意加空格)

伪操作:

area reset ,code,readonly

code32

entry

end

area: 这是最重要的一个伪操作,用于定义一个段。程序、数据、堆栈等都需要被组织在不同的段中。

reset: 这是你为这个段起的名字。名字 reset 具有很强的暗示性,通常用于表示复位向量段,即CPU上电或复位后首先执行的第一段代码所在的位置。

code: 指定该段的属性为代码,意味着这个段包含可执行的指令。

readonly: 指定该段的属性为只读。对于代码段来说,这通常是默认且必须的。

code32: 表示后续指令使用 32位的 ARM 指令集。

thumb: 表示后续指令使用 16位的 Thumb 指令集。

2.指令

1.mov

MOV{S}<c> <Rd>, #<const>

MOV{S}<c> <Rd>, <Rm>
注意:#<n>/<Rs> 取值范围 (0 - 31)

MOV instruction Canonical form

MOV{S} <Rd>, <Rm>, ASR #<n> ASR{S} <Rd>, <Rm>, #<n>

MOV{S} <Rd>, <Rm>, LSL #<n> LSL{S} <Rd>, <Rm>, #<n>

MOV{S} <Rd>, <Rm>, LSR #<n> LSR{S} <Rd>, <Rm>, #<n>

MOV{S} <Rd>, <Rm>, ROR #<n> ROR{S} <Rd>, <Rm>, #<n>

MOV{S} <Rd>, <Rm>, ASR <Rs> ASR{S} <Rd>, <Rm>, <Rs>

MOV{S} <Rd>, <Rm>, LSL <Rs> LSL{S} <Rd>, <Rm>, <Rs>

MOV{S} <Rd>, <Rm>, LSR <Rs> LSR{S} <Rd>, <Rm>, <Rs>

MOV{S} <Rd>, <Rm>, ROR <Rs> ROR{S} <Rd>, <Rm>, <Rs>

MOV{S} <Rd>, <Rm>, RRX RRX{S} <Rd>, <Rm>

例:mov r0,#0x8

mov r1,r0

2.add(加法)

立即数作为第二操作数: ADD{S}<c> <Rd>, <Rn>, #<const>

寄存器作为第二操作数寄存器: ADD{S}<c> <Rd>, <Rn>, <Rm>{, <shift>}

寄存器作为第二操作数移位量: ADD{S}<c> <Rd>, <Rn>, <Rm>, <type> <Rs>

例:add r6,r0,#0xF0

add r7,r0,r1

add r7,r0, r1, lsl #1

add r7, r0, r1, lsl r2

3.sub(减法)

立即数作为第二操作数: SUB{S}<c> <Rd>, <Rn>, #<const>

寄存器作为第二操作数寄存器: SUB{S}<c> <Rd>, <Rn>, <Rm>{, <shift>}

寄存器作为第二操作数移位量: SUB{S}<c> <Rd>, <Rn>, <Rm>, <type> <Rs>

和add类似

4.ldr(加载指令)

LDR<c> <Rt>, <label>

5.mvn(按位取反移动指令)

MVN{S}<c> <Rd>, #<const>{, <shift>}

MVN{S}<c> <Rd>, <Rm>

MVN{S}<c> <Rd>, <Rm>, <type> <Rs>

6.bic(bit clear):指定位清零

BIC{S}<c> <Rd>, <Rn>, #<const>

BIC{S}<c> <Rd>, <Rn>, <Rm>{, <shift>}

BIC{S}<c> <Rd>, <Rn>, <Rm>, <type> <Rs>

例:

mov r0, #0xFFFFFFFF

mov r1, #1

bic

7.循环

(1)do...while(C)

int i = 0;

int sum = 0;

do{

sum += i;

i++;

}while(i <= 100)

汇编:

mov r0, #0

mov r1, #0

loop

add r1, r1, r0

add r0, r0, #1

cmp r0, #100

ble loop

(2)int i = 0;

int sum = 0;

while(i <= 100)

{

sum += i;

i++;

}

汇编:while;

mov r0, #1

mov r1, #0

lable

cmp r0, #1000

bgt finish

add r1, r1, r0

add r0, r0, #1

b lable

3.立即数

1.定义:计算机指令中直接包含在指令本身中的常数值,是CPU在执行指令时可以直接使用的数值,一般小于255的数

  1. 12位立即数判断标准:把某个数展开成2进制,该数必须存在一种循环右移(偶数位),使得移位后高24位全0,低8位即为有效imm8;

4.b, bl, bx 的区别

|----|---------------------------|-------------------------------------------|
| 类型 | 功能 | 特点 |
| b | 最简单的跳转,类似于goto | 不保存返回地址, 不会自动返回 用于循环、条件分支、函数内跳转 |
| bl | 跳转到目标地址, 将下一条指令地址保存到LR寄存器 | 用于函数调用, 被调函数通常以 bx lrmov pc, lr 返回 |
| bx | 跳转到寄存器指定的地址, | 目标地址由寄存器指定(间接跳转) 常用于函数返回和模式切换 |

5.ARM内核采用的栈

默认采用满减栈:栈顶指针SP始终指向已存数据的最后一个位置(栈非空时,SP指向有效数据);

栈增长方向为地址递减,入栈时SP先减4再存入数据,出栈时先读取数据,SP再加4

6.CPSR中条件标志位,分别在什么情况下被置位

|-----|--------|--------------------------------------|
| 标志位 | 名称 | 置位条件 |
| N | 符号位标志位 | 最高位位1,结果位负时 |
| Z | 零值标记位 | 结果为0 |
| C | 进位标志位 | 无符号:加法运算时最高位向更高位进位时或减法运算时最高位无借位(大-小) |
| V | 溢出标志位 | 有符号:"两个正数相加得负数" 或 "两个负数相加得正数" |

7.arm汇编调用c语言函数以及c语言函数调用汇编编写的函数,函数参数和返回值如何处理?

(1)arm汇编调用C语言

函数参数:

1.前四个参数依次放在r0,r1,r2,r3

2.如果参数超过四个,多余的参数会从右到左依次压入栈中

返回值:

通过寄存器r0返回

(2)C语言调用汇编

函数参数:

与汇编调用C语言一致

返回值:

汇编函数直接读取寄存器或栈位置

需保存被调用的寄存器(r0-r12,lr)

相关推荐
CODECOLLECT4 小时前
京元 I62D Windows PDA 技术拆解:Windows 10 IoT 兼容 + 硬解码模块,如何降低工业软件迁移成本?
stm32·单片机·嵌入式硬件
BackCatK Chen5 小时前
STM32+FreeRTOS:嵌入式开发的黄金搭档,未来十年就靠它了!
stm32·单片机·嵌入式硬件·freertos·低功耗·rtdbs·工业控制
万法若空6 小时前
8086/8088实模式的内存布局
汇编
全栈游侠7 小时前
STM32F103XX 02-电源与备份寄存器
stm32·单片机·嵌入式硬件
Lsir10110_7 小时前
【Linux】中断 —— 操作系统的运行基石
linux·运维·嵌入式硬件
陌上花开缓缓归以8 小时前
LiteOS和RTOS 系统选型分析
arm开发
深圳市九鼎创展科技10 小时前
瑞芯微 RK3399 开发板 X3399 评测:高性能 ARM 平台的多面手
linux·arm开发·人工智能·单片机·嵌入式硬件·边缘计算
辰哥单片机设计10 小时前
STM32项目分享:车辆防盗报警系统
stm32·单片机·嵌入式硬件
小龙报11 小时前
【51单片机】从 0 到 1 玩转 51 蜂鸣器:分清有源无源,轻松驱动它奏响新年旋律
c语言·数据结构·c++·stm32·单片机·嵌入式硬件·51单片机
范纹杉想快点毕业11 小时前
嵌入式与单片机开发核心学习指南——从思维转变到第一性原理的深度实践
单片机·嵌入式硬件