SPI完整讲解(二)

SPI初始化结构体介绍

跟其它外设一样,STM32标准库提供了SPI初始化结构体及初始化 函数来配置SPI外设.初始化结构体及函数定义在库文件“stm32f10x_spi.h” 及“stm32f10x_spi.c”中,编程时我们可以结合这两个文件内的注释使用或参考库帮助文档.
配置完这些结构体成员后,要调用SPI_Init函数把这些参数写入到寄存器中,实现SPI的初始化,然后调用SPI_Cmd来使能SPI外设

typedef struct
{
  uint16_t SPI_Direction;    //设置SPI的单双向模式

  uint16_t SPI_Mode;         //设置SPI的主/从机端模式

  uint16_t SPI_DataSize;      //设置SPI的数据帧长度,可选8/16位
  uint16_t SPI_CPOL;           //设置时钟极性CPOL,可选高低电平

  uint16_t SPI_CPHA;           //设置时钟相位,可选奇/偶边沿采样
  uint16_t SPI_NSS;            //设置NSS引脚有SPI硬件控制还是软件控制
  uint16_t SPI_BaudRatePrescaler;  //设置时钟分频因子,fpclk/分频数=fSCK;
 
  uint16_t SPI_FirstBit;  //设置MSB/LSB先行         

  uint16_t SPI_CRCPolynomial;      //设置CRC校验的表达式
}SPI_InitTypeDef;

SPI_Direction:本成员设置SPI的通讯方向,可设置为双线全双工 (SPI_Direction_2Lines_FullDuplex),双线只接收 (SPI_Direction_2Lines_RxOnly),单线只接收(SPI_Direction_1Line_Rx),单线只发送(SPI_Direction_1Line_Tx).

SPI_Mode:本成员设置SPI工作在主机模式(SPI_Mode_Master)或从机模式 (SPI_Mode_Slave ),这两个模式的最大区别为SPI的SCK信号线的时序,SCK 的时序是由通讯中的主机产生的.若被配置为从机模式,STM32的SPI外设将接 受外来的SCK信号。

SPI_DataSize:本成员可以选择SPI通讯的数据帧大小是为8位(SPI_DataSize_8b)还是16(SPI_DataSize_16b).

SPI_CPOL和SPI_CPHA:时钟极性CPOL成员,可设置为高电平(SPI_CPOL_High)或低电平 (SPI_CPOL_Low ). 时钟相位CPHA 则可以设置为SPI_CPHA_1Edge(在SCK的奇数边沿采 集数据) 或SPI_CPHA_2Edge (在SCK的偶数边沿采集数据)

SPI_NSS :本成员配置NSS引脚的使用模式,可以选择为硬件模式 (SPI_NSS_Hard )与软件模式(SPI_NSS_Soft ),在硬件模式中的SPI片选信号 由SPI硬件自动产生,而软件模式则需要亲自把相应的GPIO端口拉高或置低产生非片选和片选信号。

SPI_BaudRatePrescaler :本成员设置波特率分频因子,分频后的时钟即为SPI的SCK信号线的时钟频率.这个成员参数可设置为fpclk的2、4、6、8、16、32、64、128、256分频.

SPI_FirstBit :所有串行的通讯协议都会有MSB先行(高位数据在前)还是LSB先行(低位 数据在前)的问题,而STM32的SPI模块可以通过这个结构体成员,对该特性编程控制,
SPI_CRCPolynomial:这是SPI的CRC校验中的多项式,若我们使用CRC校验时,就使用这个 成员的参数(多项式),来计算CRC的值.

FLASH芯片介绍

我的普中开发板用的是W25Q64flash芯片,
在这里插入图片描述
CS引脚对应NSS引脚,DO引脚对应MISO引脚,DI引脚对应MOSI引脚,WP引脚是写保护引脚,HOLD是通讯暂停引脚,CLK是输入时钟引脚,最高是80Mhz
在这里插入图片描述
该Flash芯片分为128个块(64KB),每个块又分为16个扇区(KB),Flash芯片在写入之前必须先擦除,擦除的操作就是把所有的数据位改成1,写入数据时只能把数据位为1的数据改为0,一般时擦除时必须按最小单位扇区来擦除(要发送扇区的起始地址),norflash可以一个字节写入,nanfflash必须以块或扇区单位进行读写,我们的芯片是norflash芯片
在这里插入图片描述
flash的状态寄存器,当我们写或者读时要判断flash的内部读写是否完成,可以BUSY状态位来判断,EEPROM也需要进行这样的判断,BUSY位的读取需要我们通过芯片的引脚发送特定的命令来获取
在这里插入图片描述
在这里插入图片描述
见上图当我们发送05h给flash芯片时,我们获取的是S0-S7的值,当我们发送35h给芯片时,我们获取的是S8-S15的值,如果我们没有结束通讯的话会一直返回状态寄存器的值,当发送20h,会擦除一个扇区,后面跟着的3个字节为开始擦除的起始地址,随后我们可以访问状态寄存器是否擦除完成,擦除完成即可写入数据,写入数据要发出02h命令,
接着的三个字节为要写入的起始地址,最后一个字节为写入的数据,当我们需要读数据要发出03h命令,后面的三个字节为我们要读取的起始地址,最后一个字节为读到的数据
在这里插入图片描述
上图主要用来读取厂家ID和设备ID发出的命令,厂家ID和设备用来开机检测是否连接到正常的芯片,我们可以发出命令来读取厂家ID和设备ID,检查是否和芯片手册里面的值一致从而做出判断,最后强调一下,EEPROM 支持的页写入只是一种加速的 I2C 的传输时序,实际上并不要求
每次都以页为单位进行读写,EEPROM 是支持随机访问的(直接读写任意一个地址),, 如前面的单个字节写入。在某些存储器,如 NAND FLASH,它是必须按照 Block写入的, 例如每个 Block 为 512 或 4096 字节,数据写入的最小单位是 Block,写入前都需要擦除整 Block,NOR FLASH 则是写入前必须以 Sector/Block 为单位擦除,然后才可以按字节写 入.而我们的 EEPROM数据写入和擦除的最小单位是“字节”而不是“页”,数据写入前 不需要擦除整页.

发布了83 篇原创文章 · 获赞 3 · 访问量 1244

猜你喜欢

转载自blog.csdn.net/qq_41936794/article/details/105280538
SPI
今日推荐