汇编点灯练习

要求:

1、轮流将LED1、LED2、LED3及蜂鸣器点亮

2、基于STM32MP157AAA,阅读原理图和STM32MP157芯片手册

3、ARM汇编指令点灯

1、运行效果

汇编点灯

2、通过查询原理图和芯片手册,得到以下结论:

3、汇编源码

cpp 复制代码
.text 
.global _start
_start:
@R0 存放寄存器在内存中的map地址
@R1 存放寄存器的值

@1 配置RCC: LD1、LD2、LD3和蜂鸣器的使能
ldr R0, =(0x50000000+0xA28)
ldr R1, [R0]
orr R1, R1, #0x32
str R1, [R0]

@2 配置MODER寄存器
@2.1 配置LED1、LED3
ldr R0, =0x50006000
ldr R1, [R0]
bic R1, #(0x33<<16)
orr R1, #(0x11<<16)
str R1, [R0]
@2.2 配置LED2
ldr R0, =0x50007000
ldr R1, [R0]
bic R1, #(0x3<<20)
orr R1, #(0x1<<20)
str R1, [R0]
@2.3 配置蜂鸣器
ldr R0, =0x50003000
ldr R1, [R0]
bic R1, #(0x3<<12)
orr R1, #(0x1<<12)
str R1, [R0]

@3 配置OTYPER寄存器
@3.1 配置LED1、LED3
ldr R0, =(0x50006000+0x04)
ldr R1, [R0]
bic R1, #(0x5<<8)
str R1, [R0]
@3.2 配置LED2
ldr R0, =(0x50007000+0x04)
ldr R1, [R0]
bic R1, #(0x1<<10)
str R1, [R0]
@3.3 配置蜂鸣器
ldr R0, =(0x50003000+0x04)
ldr R1, [R0]
bic R1, #(0x1<<6)
str R1, [R0]

@4 配置OSPEEDR寄存器
@4.1 配置LED1、LED3
ldr R0, =(0x50006000+0x08)
ldr R1, [R0]
bic R1, #(0x33<<16)
str R1, [R0]
@4.2 配置LED2
ldr R0, =(0x50007000+0x08)
ldr R1, [R0]
bic R1, #(0x3<<20)
str R1, [R0]
@4.3 配置蜂鸣器
ldr R0, =(0x50003000+0x08)
ldr R1, [R0]
bic R1, #(0x3<<12)
str R1, [R0]

@5 配置PUPDR寄存器
@5.1 配置LED1、LED3
ldr R0, =(0x50006000+0x0C)
ldr R1, [R0]
bic R1, #(0x33<<16)
str R1, [R0]
@5.2 配置LED2
ldr R0, =(0x50007000+0x0C)
ldr R1, [R0]
bic R1, #(0x3<<20)
str R1, [R0]
@5.3 配置蜂鸣器
ldr R0, =(0x50003000+0x0C)
ldr R1, [R0]
bic R1, #(0x3<<12)
str R1, [R0]

@死循环让
loop:
	bl bee_off
	bl led1_on
	bl delay	
	bl led1_off
	bl led2_on
	bl delay
	bl led2_off
	bl led3_on
	bl delay
	bl led3_off
	bl bee_on
	bl delay
	b loop

delay:
	mov R10, #0x10000000
d2:
	sub R10, R10, #1
	cmp R10, #0
	bne d2
	mov PC, LR

led1_on:
ldr R0, =(0x50006000+0x14)
ldr R1, [R0]
orr R1, #(0x1<<10)
str R1, [R0]
mov PC, LR

led2_on:
ldr R0, =(0x50007000+0x14)
ldr R1, [R0]
orr R1, #(0x1<<10)
str R1, [R0]
mov PC, LR

led3_on:
ldr R0, =(0x50006000+0x14)
ldr R1, [R0]
orr R1, #(0x1<<8)
str R1, [R0]
mov PC, LR

bee_on:
ldr R0, =(0x50003000+0x14)
ldr R1, [R0]
orr R1, #(0x1<<6)
str R1, [R0]
mov PC, LR

led1_off:
ldr R0, =(0x50006000+0x14)
ldr R1, [R0]
bic R1, #(0x1<<10)
str R1, [R0]
mov PC, LR

led2_off:
ldr R0, =(0x50007000+0x14)
ldr R1, [R0]
bic R1, #(0x1<<10)
str R1, [R0]
mov PC, LR

led3_off:
ldr R0, =(0x50006000+0x14)
ldr R1, [R0]
bic R1, #(0x1<<8)
str R1, [R0]
mov PC, LR

bee_off:
ldr R0, =(0x50003000+0x14)
ldr R1, [R0]
bic R1, #(0x1<<6)
str R1, [R0]
mov PC, LR

.end

4、疑问

4.1 汇编代码优化

从源码中可以看出,其实有大量的重复代码,作为一名"资深"程序员,很想抽成一个一个的函数。但是实际中,这样做一定有大量的push/pop操作,而且如果程序段跨度过大,代码段的交替跳转,有可能还会影响程序执行效率(CPU会将执行代码的前后一段调入到多级缓存中,以提升执行效率)。

因此,在编写汇编的时候,应该遵循执行效率优先,还是可读性和可复用性呢?

4.2 一段反汇编代码

如图所示, =(0x50000000+0xA28)被译成了[pc, #444], 不太理解。

相关推荐
千千道8 小时前
linux的线程同步(条件变量和锁)
linux·arm开发·驱动开发·物联网·arm
湘の子11 小时前
汇编语言与接口技术--跑马灯
汇编·stm32·单片机·嵌入式硬件·51单片机
肖无疾1 天前
在CE自动汇编里调用lua函数
汇编·lua·ce
矮油0_o3 天前
30天开发操作系统 第 10 天 -- 叠加处理
开发语言·汇编·数据结构·c++·算法·操作系统
一品人家4 天前
win32汇编环境下,对话框程序中生成listview列表控件,点击标题栏自动排序的示例
汇编·windows·microsoft
一品人家4 天前
win32汇编环境下,提取对话框程序中,listview列表控件里的内容示例
汇编·microsoft
一品人家4 天前
win32汇编环境下,双击窗口程序内生成的listview列表控件的某行,并提取其内容的示例程序
汇编
代码巨匠5 天前
汇编指令总结、练习、C与汇编混合使用
汇编
阿隆ALong5 天前
云手机:小红书矩阵搭建方案
线性代数·智能手机·矩阵·云计算·arm