imx6ull LED bring up 裸机实验(电子电路硬件知识)
一.LED点亮基础
首先,课程的角度,老师说的是当gpio输出低电平,LED会点亮,当gpio输出高电平,LED会灭,(高低电平指的是电压)。可能部分人不太理解这里的电子电路硬件原理。在电路设计里,一般有两种实现led点亮的硬件设计。
1.gpio输出低电平点亮LED
+Vcc (电源正极) –[限流电阻]–|–> LED –|–> GPIO引脚
|
GND (电源负极)
在这个电路中,当GPIO引脚输出低电平时(0V或接近0V),以下情况会发生:
LED两端存在电压差(Vcc – 0V),电流可以通过LED,使其点亮。
当GPIO引脚输出高电平时(通常是Vcc或接近Vcc),以下情况会发生:
LED两端的电压差接近0V(Vcc – Vcc),没有足够的电压推动电流通过LED,因此LED不会点亮。
这种连接方式称为“共阳极”连接,即LED的阳极(正极)连接到电源正极。在这种情况下,GPIO输出低电平时LED亮,输出高电平时LED灭。
2.gpio输出高电平点亮LED
GPIO引脚–|–> LED –[限流电阻]–|–> GND (电源负极)
|
+Vcc (电源正极)
如果你遇到的情况是GPIO输出高电平时LED灭,输出低电平时LED亮,那么你的LED可能是以这种方式连接的。如果你期望相反的行为,那么你需要改变LED的连接方式,即使用“共阴极”连接:
在共阴极连接中,当GPIO引脚输出低电平时,LED两端没有电压差,因此LED不亮;当GPIO引脚输出高电平时,电流可以通过LED,使其点亮。
总之,LED的亮灭状态取决于GPIO引脚的输出电平和LED的连接方式。
二.使能时钟
1.什么是时钟?时钟的作用?
官方的解释在哪都能搜索的到。以下是本人的理解,这就像是个类比,使能时钟是就像给人活着所需的地球环境,任何操作都必须先有活着的地球环境才可以执行。所以这是第一步
2.CCGR0-6 控制所有外设的使能,这句话是什么意思?
我们知道针对这LED,是对GPIO进行时钟使能。其实就是对有所有芯片引脚进行时钟使能,而这些引脚可以用作I2C,SPI,GPIO,定时器等等功能控制外部设备,对他们使能其实就是对外设进行使能。所以有了 CCGR0-6 控制所有外设的使能。
三.思维导图
四.汇编编写程序加个人理解
1.使能所有时钟
这里只写初始化CCM_CCGR0
ldr r0, =0X020C4068 //r0和r1都是存储寄存器,本质上没有什么区别。ldr都是将内存数据存储到rx存储寄存器里。但有一种通用的约定,r0代表的是存储的内存地址所指的 寄存器(非存储寄存器)。而r1才是实际存储数据的存储寄存器。
ldr r1, =0XFFFFFFFF
str r1, [r0] //这里就是将r1的数据存储到r0存储的内存地址所指向的寄存器里。
//ldr新语法讲解
ldr r0, =0X020C4068
ldr r1, [r0]
*解析:总体含义是将r0存储的内存地址所指的 寄存器的值 加载到 r1存储寄存器里。
所以这里我们可以理解,[rx]-->代表的是 “rx存储的内存地址所指的 寄存器”
画个简陋流程图即:rx存储的值是 0X020C4068 ->通过 []->指向内存地址0X020C4068的寄存器
-
rx存储的值是 0X020C4068 ->通过 []->指向内存地址0X020C4068的寄存器
2.如下是我自己的汇编程序,在电灯基础上实现流水灯。
.global _start /* 全局标号 */
/*
* 描述: _start函数,程序从此函数开始执行此函数完成时钟使能、
* GPIO初始化、最终控制GPIO输出低电平来点亮LED灯。
*/
_start:
/* 使能GPIO是时钟,使能所有外设时钟 CCM_CCGR0-6 */
ldr r0, =0x020c4068 /* CCGR0 */
ldr r1, =0xffffffff
str r1, [r0]
ldr r0, =0x020c406c /* CCGR1 */
ldr r1, =0xffffffff
str r1, [r0]
ldr r0, =0x020c4070 /* CCGR2 */
ldr r1, =0xffffffff
str r1, [r0]
ldr r0, =0x020c4074 /* CCGR3 */
ldr r1, =0xffffffff
str r1, [r0]
ldr r0, =0x020c4078 /* CCGR4 */
ldr r1, =0xffffffff
str r1, [r0]
ldr r0, =0x020c407c /* CCGR5 */
ldr r1, =0xffffffff
str r1, [r0]
ldr r0, =0x020c4080 /* CCGR6 */
ldr r1, =0xffffffff
str r1, [r0]
/* 配置复用寄存器为GPIO 配置电器属性 */
ldr r0, =0x020e0068 /* 复用寄存器SW_MUX_CTL_PAD_GPIO1_IO03 */
ldr r1, =0x00000005
str r1, [r0]
/* 3、配置GPIO1_IO03的IO属性
*bit 16:0 HYS关闭
*bit [15:14]: 00 默认下拉
*bit [13]: 0 kepper功能
*bit [12]: 1 pull/keeper使能
*bit [11]: 0 关闭开路输出
*bit [7:6]: 10 速度100Mhz
*bit [5:3]: 110 R0/6驱动能力
*bit [0]: 0 低转换率
*/
ldr r0, =0x020e02f4 /*配置电器属性 SW_PAD_CTL_PAD_GPIO1_IO03 */
ldr r1, =0xa0
str r1, [r0]
/* 将gpio配置为通用输出,输出高电平 */
ldr r0, =0x0209c004 /*配置GPIO属性 GPIO1_GDIR 配置为输出 */
ldr r1, =0x8
str r1, [r0]
flash:
bl led_on
bl delay
bl delay
bl delay
bl led_off
bl delay
bl delay
bl delay
b flash
// 延时函数:函数名:delay
delay:
ldr r2, =9000000
ldr r3, =0x0
delay_loop:
sub r2, r2, #1 //r2 = r2 -1
cmp r2, r3 // cmp会影响Z标志位,如果r2等于r3则Z=1,下一句中eq就会成立
bne delay_loop
mov pc, lr // 函数调用返回
led_on:
ldr r0, =0x0209c000 /*配置GPIO属性 GPIO1_DR 输出低电平 亮 */
ldr r1, =0
str r1, [r0]
mov pc, lr
led_off:
ldr r0, =0x0209c000 /*配置GPIO属性 GPIO1_DR 输出高电平 灭*/
ldr r1, =0xffffffff
str r1, [r0]
mov pc, lr
作者:阿伦798