【STM32】SPI通信和RTC实时时钟

2024-08-14 14:38:34 浏览数 (2)

SPI通信

一、简介

有四根通信线SCK(Serial Clock 串行时钟线)、MOSI(Master Output Slave Input 主机输出从机输入)、MISO(Master Input Slave Output 主机输入从机输出)、SS(Slave Select 从机选择)

同步时序(SCK),全双工(MOSI、MISO)

支持总线挂载多设备,是一主多从,有一条专门用来进行从机选择的线(SS),一机一根

二、硬件电路

看清楚箭头,箭头是传输方向

每有一个从机,SPI主机都要引出一根SS线连接

这里的端口电压为比较电压,是相对于GND的电压,所以所有设备需要共地,如果从机没有电源的话,还需要从主机VCC连接线来供电

主机通过置SS为低电平选择从机进行通信,在初始状态时,主机的所有SS引脚都为高电平,且在同一时间只能与一个从机进行通信

输出引脚配置为推挽输出,输入引脚配置为浮空输入或上拉输入

三、基本原理

SPI通信的基本原理就是进行移位交换

首先波特率发生器存在于主机,由主机控制,通过SLK线使从机同步时序,移位寄存器都是向左移位,移出后在MOSI和MISO产生相应的电平变化,如下图所示

向左移位移出,同时通信线发生移出数字相应的电平变化,然后再写入

如此往复八次就能实现一个字节的迁移,这是同时发送接收的情况

在只进行发送和只进行接收的时候,也是一样的移位和迁移,但只进行发送时,此时从机移位寄存器中的值为无效值,通常为0x00或0xFF,只进行接收的时候,主机移位寄存器中的值为无效值

四、SPI时序

起始条件:SS从高电平切换到低电平 终止条件:SS从低电平切换到高电平

1、时序基本单元

CPOL时钟极性 CPHA时钟相位

CPOL

CPHA

模式

说明

0

0

模式0

空闲状态时,SCK为低电平;SCK第一个边沿移入数据,第二个边沿移出数据

0

1

模式1

空闲状态时,SCK为低电平;SCK第一个边沿移出数据,第二个边沿移入数据

1

0

模式2

空闲状态时,SCK为高电平;SCK第一个边沿移入数据,第二个边沿移出数据

1

1

模式3

空闲状态时,SCK为高电平;SCK第一个边沿移出数据,第二个边沿移入数据

在SS由高电平切换到低电平后,在SCK第一个边沿(CPOL=0是上升沿,CPOL=1是下降沿)之前,MOSI和MISO开始变换电平,在第一个边沿移入(CPHA=0,CPHA=1为移出)数据,然后在第二个边沿(CPOL=0是下降沿,CPOL=1是上升沿)移出(CPHA=0,CPHA=1为移出)数据

但是在CPHA=0的情况下,第一个数据还没有移出肯定是没有办法移入的,所以在SS下降沿时,在SCK第一个边沿之前就要触发移出数据,移出数据是对应着MOSI和MISO上升或下降沿的

2、时序

SPI的时序与I2C的时序基本相同,有些细微的差别,不多赘述

五、FLASH操作注意事项

1、写入操作

写入操作之前要先进行使能

每个数据位只能由1改写为0,不能由0改写为1

写入数据前必须先擦除,擦除后,所有数据位变为1,因为这样可以使再写入的数据保持原样

擦除必须按最小擦除单元(一个扇区)进行,没办法只擦除一个指定字节,只能整片一起擦,除非该扇区只存储了这一个字节

连续写入多字节时,最多写入一页的数据(缓冲区存储),超过页尾位置的数据会回到页首覆盖写入

写入(或者擦除)操作结束后,芯片进入忙状态,不响应新的读写操作,忙状态就是缓冲区向FLASH写入的这个状态,读取状态寄存器,如果BUSY位为1,就是忙状态,如果为0,就不是忙状态了,就可以继续响应新的操作了

2、读取操作

直接调用读取时序,无需使能,无需额外操作,没有页的限制,读取操作结束后不会进入忙状态,但不能再忙状态时读取

六、SPI外设

1、简介

STM32内部集成了硬件SPI收发电路,可以由硬件自动执行时钟生成、数据收发等功能、减轻CPU的负担

时钟频率只能为外部时钟除以2,4,8,16,32,64,128,256来得到

支持多主机模型或一主多从模型

可精简为半双工或单工通信,半双工就是在SPI的两条通信线中选择一条进行双向通信,类似于I2C,单工通信就是指去除SPI两根通信线的某一根,另一根功能不变

2、结构

先看左上角红色方框,这里是一个重叠电路,因为MOSI在设备时主机时输出是从机时输入,MISO同理,所以在设备做主机和从机时所走的线路不一样,因为接在移位寄存器上的线路是不变的,所以我们要改变前面的线路,在做主机时,就是从蓝色的线直接进出,做从机时输出,就在上方蓝线经过红色方框的电路时走到下方的棕色线上去,然后从MISO输出,输入就是从MOSI进入时走下方棕色线到移位寄存器

然后绿色椭圆就是发送接收的缓冲区以及移位寄存器,LSBFIRS控制位控制移位为左移还是右移,要发送的数据写入发送缓冲区后一位一位地移入移位寄存器,然后再由移位寄存器一位一位地移出,此时TXE和RXNE的变化与USART串口的相同,不过串口有两个移位寄存器,这里只有一个

下方的蓝色椭圆中就是波特率发生器,外接时钟,可以如上面所说的按照指定比例分频,与移位寄存器时序相同,这里的波特率发生器由绿色方框中的BR0、BR1、BR2共同控制

最后就是蓝色方框以及绿色方框中的寄存器,我们可以看到蓝色方框中我们熟悉的寄存器如TXE和RXNE,绿色方框中的CPOL、CPHA

七、传输方式

连续传输适用于高性能、高要求的传输,相应地,其代码也要更加复杂,如果没有严格要求,可以使用非连续传输,更简单一些

1、主模式全双工连续传输
这里的BSY标志就是上面提到的BUSY

发送: 开始时TXE为1,表示发送缓冲器TDR为空,可以写入并传输,然后看下方的指示,发送缓冲器TDR被写入0xF1,同时TXE置0,然后发送缓冲器TDR中的数据会转入移位寄存器,此时TXE置为1,然后移位寄存器就开始发送,波形开始生成

然后按照下方指示2,写入0xF1之后,软件等待TXE=1,也就是在发送缓冲器TDR中的数据转入到移位寄存器时,写入发送缓冲器TDR第二个数据0xF2,当第一个数据0xF1发送完毕后,第二个数据0xF2就转入到移位寄存器中发送,同时第三个数据再写入发送缓冲器TDR,以此类推

当发送最后一个数据时,最后一个数据转入移位寄存器后TXE置为1,当BSY标志位0时,表示当前不忙,也就是发送完毕

接收: 当第一个数据接收完成时,转入接收缓冲器RDR,转入的同时RXNE置1,检测到RXNE为1时就读出RDR,等CPU读出后,RXNE置0,重复上述过程,读取多个数据

RDR中的数据在写入后要尽快读走,要在下一个数据写入之前,因为RDR再被写入前一个数据就会被覆盖

2、非连续传输

该图只有输出,没有输入,因为非连续传输的原理比较简单,一发一收

发送: 这里跟上面其实是一样的,只不过在这里主要看BSY位,因为非连续传输不需要连续,所以一个数据写入TDR后,移位到移位寄存器发送,此时TDR为空,但此时不需要再写入新的数据到TDR中,在BSY位置为0时再写入,然后重复上述过程

接收: 输入就更简单了,当数据写入移位寄存器后,由移位寄存器转移到RDR中,此时不用紧跟着数据写入移位寄存器,而是在移位寄存器RDR中的数据读出后,再继续写入下一个数据到移位寄存器,重复上述过程

RTC实时时钟

一、Unix时间戳

Unix时间戳定义为伦敦时间从1970年1月1日0时0分0秒开始所经过的秒数

时间戳存储在一个秒计数器中,秒计数器为32位或64位的变量 也就是说,如果该变量为无符号型,也就是它所能承受的最大值为2^32-1或2 ^64-1,后面这个数字是非常大的,宇宙级别的时间,所以现在随着科技的进步,很多设备都给上64位的版本了

世界上所有时区的秒计数器相同,不同时区通过添加偏移量来得到当地时间,这个偏移量其实就是时差 0秒标志着伦敦时间1970年1月1日0时0分0秒,北京时间1970年1月1日8时0分0秒

二、BKP

1、简介

BKP就是备份寄存器,可用于存储用户应用程序数据,当VDD电源(系统主电源2.0~3.6V)被切断,它们仍然由VBAT(备用电池电源1.8 ~ 3.6V)维持供电,当系统在待机模式下被唤醒,或系统复位或电源复位时,它们也不会被复位

TAMPER引脚产生的侵入事件将所有备份寄存器内容清除(这是一个保护功能,防拆作用)

RTC引脚输出RTC校准时钟、RTC闹钟脉冲或秒脉冲

存储RTC时钟校准寄存器

用户数据存储容量为20字节(小容量和中容量设备)或84字节(大容量和互联型设备)

2、基本结构

BKP先通过VDD进行供电,在有主电源VDD的情况下优先使用主电源供电

数据寄存器是16位的,每个寄存器可以存储两字节,小容量和中容量的设备一般有10个数据寄存器,从DR1到DR10,大容量和互联型的设备一般有42个数据寄存器,从DR1到DR42

因为BKP与RTC联系紧密,所以BKP中有控制RTC的部分

三、RTC

1、简介

RTC就是实时时钟,是一个独立地定时器,可为系统提供时钟和日历的功能

RTC和时钟配置系统处于后备区域,系统复位时数据不清零,VDD断电后可借助VBAT供电继续走时(同BKP)

32位的可编程计数器,可对应Unix时间戳的秒计数器

20位的可编程预分频器,可适配不同频率的输入时钟

可选择三种RTC时钟源: HSE(外部高速晶振)时钟除以128 LSE(外部低速晶振)振荡器时钟(主要使用,只有这个连接着备用电源) LSI(内部低速晶振)振荡器时钟

2、基本结构

RTC时钟外接一个RTCCLK,一般是外部低速晶振,红色方框里的就是一个预分频器,与前面介绍过的预分频器其实是一种类型,并且实现方式相同,只是这里用了不同的名字

然后就是绿色方框里的就是一个32位的可编程计数器,是无符号32位,最多使用到2106年,到时候就会发生溢出,就可以产生一个溢出中断,也就是RTC_Overflow中断,绿框中还一个闹钟设备RTC_ALR,给它定一个时间,当CNT==ALR时,就会触发RTC_Alarm中断,也可以通过下面的线退出待机模式,最后还有一个中断就是RTC_Second中断,是每秒进一个中断

右边的三个中断,F结尾的是对应的中断标志位,IE结尾的是中断使能,凉凉通过一个与门,之后三个中断连接到一个或门连接NVIC中断控制器

上图就是RTC外部电路,一个是备用电池供电,一个是外部低速晶振

备用电池在标准下应该用推荐连接,这里在电路上有两个二极管,这两个二极管的作用就是防止电流倒灌,在有外接电源时,使用3.3V的外部电源,在无外部电源时,使用备用电池B2供电,外部还需要接一个0.1uF的滤波电容

3、注意事项

设置RCC_APB1ENR的PWREN和BKPEN,使能PWR和BKP时钟 设置PWR_CR的DBP,使能对BKP和RTC的访问

若在读取RTC寄存器时,若RTC的APB1接口处于禁止状态,则软件首先必须等待RTC_CRL寄存器中的RSF位(寄存器同步标志)被硬件置1

必须设置RTC_CRL寄存器中的CNF位,使RTC进入配置模式后,才能写入RTC_PRL、RTC_CNT、RTC_ALR寄存器

对RTC任何寄存器的写操作,都必须在前一次写操作结束后进行,可以通过查询RTC_CR寄存器中的RTOFF状态位,判断RTC寄存器是否处于更新中,仅当RTOFF状态位为1时,才可以写入RTC寄存器 (这跟上面的忙状态差不多)

今日分享就到这里了~

0 人点赞