一、关于汇编语言
汇编语言(Assembly Language)是任何一种用于电子计算机、微处理器、微控制器或其他可编程器件的低级语言,亦称为符号语言。在汇编语言中,用助记符代替机器指令的操作码,用地址符号或标号代替指令或操作数的地址。在不同的设备中,汇编语言对应着不同的机器语言指令集,通过汇编过程转换成机器指令。特定的汇编语言和特定的机器语言指令集是一一对应的,不同平台之间不可直接移植。
二、简单汇编程序的编写
1.新建工程
我们新建一个工程,由于我使用的是STM32F103C8T8的芯片,这里选择对应的驱动
还要选择启动文件
在group里面添加一个汇编语言的.S文件
2.参考代码
AREA MYDATA, DATA
AREA MYCODE, CODE
ENTRY
EXPORT __main
__main
MOV R0, #10
MOV R1, #11
MOV R2, #12
MOV R3, #13
;LDR R0, =func01
BL func01
;LDR R1, =func02
BL func02
BL func03
LDR LR, =func01
LDR PC, =func03
B .
func01
MOV R5, #05
BX LR
func02
MOV R6, #06
BX LR
func03
MOV R7, #07
MOV R8, #08
BX LR
3.调试程序
首先,我们需要设置一下,使keil在仿真模式下运行。
点击箭头所指位置的魔法棒,在Debug选项页选中use Simulator 进入仿真模式,并将第三个箭头所指的位置改成DARMSTM.DLL和pSTM32F103C8
完成后,点击Debug和run,就可以开始调试了
与代码比对后可以发现所设置的地址一致
4.关于生成的hex文件
想要生成hex文件,记得在output里面的选项打开
在编译文件后,可以看到生成的文件的大小
打开生成的hex文件,可以看到很多数据
这里我对第一行的数据进行一定的解释
第一行数据:020000040800F2,其实质表达的是十六进制的数据0x02 0x00 0x00 0x04 0x08 0x00 0xf2
第一个字节 0x02表示本行数据的长度;
第二、三字节 0x00 0x00表示本行数据的起始地址;
第四字节0x04表示数据类型;
第五、六字节0x08 0x00表示的是数据;
第六个字节0xf2是校验和。
三、程序实操
在上述内容的基础上,使用汇编语言实现LED的闪烁
1.程序代码
;预定义
LED0 EQU 0x422201b4 ;PC13的Bit-Bond地址
RCC_APB2ENR EQU 0x40021018
GPIOA_CRH EQU 0x40011004
;分配栈空间
Stack_Size EQU 0x00000400
AREA STACK, NOINIT, READWRITE, ALIGN=3 ;汇编一个新的代码段或数据段
Stack_Mem SPACE Stack_Size ;保留一个用零填充的存储器块
__initial_sp
;分配向量表
AREA RESET, DATA, READONLY
__Vectors DCD __initial_sp ; Top of Stack
DCD Reset_Handler ; Reset Handler
;开始代码段
AREA |.text|, CODE, READONLY
THUMB
REQUIRE8
PRESERVE8
ENTRY ;声明整个程式的入口点,入口点有且仅有一个
Reset_Handler
BL LED_Init
MainLoop BL LED_ON
BL Delay
BL LED_OFF
BL Delay
B MainLoop
LED_Init
PUSH {R0,R1, LR}
LDR R0,=RCC_APB2ENR
ORR R0,R0,#0x04
LDR R1,=RCC_APB2ENR
STR R0,[R1]
LDR R0,=GPIOA_CRH
BIC R0,R0,#0XFF0FFFFF
LDR R1,=GPIOA_CRH
STR R0,[R1]
LDR R0,=GPIOA_CRH
ORR R0,R0,#0X00300000
LDR R1,=GPIOA_CRH
STR R0,[R1]
;将PC13置1
MOV R0,#1 ;将立即数1送入R0
LDR R1,=LED0
STR R0,[R1]
POP {R0,R1,PC}
;LED亮
LED_ON
PUSH {R0,R1,LR}
MOV R0,#0
LDR R1,=LED0
STR R0,[R1]
POP {R0,R1,PC}
;LED灭
LED_OFF
PUSH {R0,R1,LR}
MOV R0,#1
LDR R1,=LED0
STR R0,[R1]
POP {R0,R1,PC}
Delay
PUSH {R0,R1,LR}
MOVS R0,#0
MOVS R1,#0
MOVS R2,#0
DelayLoop0
ADDS R0,R0,#1
CMP R0,#330
BCC DelayLoop0
MOVS R0,#0
ADDS R1,R1,#1
CMP R1,#330
BCC DelayLoop0
MOVS R0,#0
MOVS R1,#0
ADDS R2,R2,#1
CMP R2,#15
BCC DelayLoop0
POP {R0,R1,PC}
NOP
END