做幼儿网站的目标,网站建设捌金手指下拉十一,服饰视频网站建设,财务管理咨询本节我们将继续学习下一个通信协议 SPI#xff0c;SPI 通信和我们刚学完的 I2C 通信差不多。两个协议的设计目的都一样#xff0c;都是实现主控芯片和各种外挂芯片之间的数据交流#xff0c;有了数据交流的能力#xff0c;我们主控芯片就可以挂载并操纵各式各样的外部芯片SPI 通信和我们刚学完的 I2C 通信差不多。两个协议的设计目的都一样都是实现主控芯片和各种外挂芯片之间的数据交流有了数据交流的能力我们主控芯片就可以挂载并操纵各式各样的外部芯片来实现一个功能更加强大的控制系统。那本节 SPI 通信的安排和上一节 I2C 的也是一样我们先学习 SPI 协议的软硬件规定先用软件模拟的 SPI实现读写 W25Q64 Flash 存储器之后我们再学习 STM32 中的 SPI 外设再用硬件 SPI 实现同样的功能。
W25Q64 是一个 Flash 存储器芯片它内部可以存储 8 M 字节的数据并且是掉电不丢失的。如果你之后的项目中需要存储大量的数据就可以考虑一下外挂这个芯片来实现。
那在这里我们用 4 根 SPI 通信线把 W25Q64 和 STM32 连接在一起STM32 操作引脚电平实现 SPI 通信的时序进而实现读写存储器芯片的目的。
那在 OLED 上我们可以看到程序测试的现象第一行显示的是 ID 号MID 是厂商 ID读出来是 0xEFDID 是设备 ID读出来是 0x4017这些 ID 号都是固定的数值在手册里有写我们用 SPI 读写 ID 号就可以进行最简单的测试了如果读取 ID 号和手册里 一样说明 SPI 通信基本没问题。之后既然是存储器芯片我们肯定就是写几个数据再读出来看看对不对了这里第二行W写的内容是 4 个字节0x01020304。然后第三行R就是读到的内容了显示出来可以看到也是 0x01020304读出来和写入的一样这说明读写存储器芯片没问题。当然更进一步的测试比如读写更多的数据、写入的数据是不是掉电不丢失这些我们之后写程序的时候再来验证。程序现象就看到这里。
1. SPI 通信简介
1.1 SPI 的基本功能
SPISerial Peripheral Interface串行外设接口是由Motorola公司开发的一种通用数据总线 和 I2C 一样它们都是通用的数据总线。同时它们也都是用于主控和外挂芯片之间的通信应用领域非常相似。当然I2C 和 SPI两者是各有优势和劣势的。在某些芯片呢我们用 I2C 更好在另一些芯片呢我们用 SPI 更好。 上一节我们学习 I2C 的时候可以发现 I2C无论是硬件电路还是软件时序设计的都是相对比较复杂的。硬件上我们要配置为开漏外加上拉的模式软件上我们有很多功能和要求比如一根通信线兼顾数据收发应答位的收发、寻址机制的设计等等最终通过这么多的设计就使得 I2C 通信的性价比非常高I2C 可以在消耗最低硬件资源的情况下实现最多的功能。在硬件上无论挂载多少个设备都只需要两根通信线在软件上数据双向通信、应答位都可以实现。如果把通信协议比作是一个人的话那 I2C 就属于精打细算、思维灵活这类型的人既要实现硬件上最少的通信线又要实现软件上最多的功能。最终I2C 通过精心的设计也确实实现了这么多功能可以说是非常的优雅。当然在这些优雅之中也隐藏了一个缺点就是我们上节说的由于 I2C 开漏外加上拉电阻的电路结构使得通信线高电平的驱动能力比较弱这就会导致通信线由低电平变到高电平的时候这个上升沿耗时比较长这会限制 I2C 的最大通信速度所以I2C 的标准模式只有 100 KHz 的时钟频率I2C 的快速模式也只有 400 KHz虽然 I2C 协议之后又通过改进电路的方式设计出了高速模式可以达到 3.4 MHz但是高速模式目前普及程度不是很高。所以一般情况下我们认为 I2C 的时钟速度最多就是 400 KHz这个速度相比较 SPI 而言还是慢了很多那了解完 I2C 的优势和缺点我们就来看一下 SPI。 在学习之前简单概括几点 SPI 相对于 I2C 的优缺点 首先SPI 传输更快SPI 协议并没有严格规定最大传输速度这个最大传输速度取决于芯片厂商的设计需求比如说我们这个 W25Q64 存储器芯片手册里写的 SPI 时钟频率最大可达 80 MHz这比 STM32F1 的主频还要高。 其次SPI 的设计比较简单粗暴实现的功能没有 I2C 那么多所以学习起来SPI 还是比 I2C 简单很多的。 最后SPI 的硬件开销比较大通信线的个数比较多并且通信过程中经常会有资源浪费的现象如果继续把通信协议比作一个人的话那 SPI 就属于富家子弟、有钱任性这类型的人SPI 说我不在乎我花了多少钱我只在乎我的任务有没有最简单、最快速的完成这就是 SPI 的风格。 好经过这么多的对比和铺垫大家对 SPI 应该就有了一个第一印象了吧。 四根通信线SCKSerial Clock串行时钟线、MOSIMaster Output Slave Input主机输出从机输入、MISOMaster Input Slave Output主机输入从机输出、SSSlave Select从机选择 这是 SPI 通信典型的引脚名称。当然在实际情况下这些名称可能会有别的表述方式。比如SCK有的地方可能叫作 SCLK、CLK、CKMOSI 和 MISO有的地方可能直接叫作 DOData Output和 DIData InputSS有的地方也可能叫作 NSSNot Slave Select、CSChip Select这些不同的名称都是一个意思大家了解一下。那这里就以 SPI 官方文档的名称为准统一都用这几个名词来表示。 那这四个引脚的意义和作用是什么呢我们继续往后看 SPI 基本特性是同步全双工 首先既然是同步时序肯定就得有时钟线了所以 SCK 引脚就是用来提供时钟信号的数据位的输出和输入都是在 SCK 的上升沿或下降沿进行的这样数据位的收发时刻就可以明确的确定。并且同步时序时钟快点慢点或者中途暂停一会儿都是没问题的这就是同步时序的好处。那对照 I2C 总线这个 SCK就相当于 I2C 的 SCL两者作用相同。 之后SPI 是全双工的协议。全双工就是数据发送和数据接收单独各占一条线发送用发送的线路接收用接收的线路两者互不影响。所以这里MOSI 和 MISO就是分别用于发送和接收的两条线路MOSI 线是主机输出从机输入如果是主机接在这条线上那就是 MO主机输出如果是从机接在这条线上那就是 SI从机输入意思就是一条通信线如果主机接在上面配置为输出那从机肯定得配置为输入才能接收主机的数据对吧。主机和从机不能同时配置为输出或输入要不然就没法通信了。所以这条 MOSI就是主机向从机发送数据的线路那同理下面这条 MISO就是主机从从机接收数据的线路这就是全双工通信的两根通信线那这两根通信线加在一起就相当于 I2C 总线的 SDA当然 I2C 是一根线兼具发送和接收是半双工。这里 SPI 是一根发送、一根接收是全双工。全双工的好处就是简单高效输出线就一直输出输入线就一直输入数据流的方向不会改变也不用担心发送和接收没协调好冲突了但是坏处就是多了一根线会有通信资源的浪费这就是全双工。 支持总线挂载多设备使用的是 一主多从 的模型 SPI 仅支持一主多从不支持多主机这一点SPI 从功能上没有 I2C 强大。那 I2C实现一主多从的方式是在起始条件之后主机必须先发送一个字节进行寻址用来指定我要跟哪个从机进行通信所以 I2C 这里要涉及分配地址和寻址的问题。但是 SPI 表示你这太麻烦了我直接大手一挥再开辟一条通信线专门用来指定我要跟哪个从机进行通信所以这条专门用来指定从机的通信线就是这里的 SS从机选择线。并且这个 SS 可能不止一条SPI 的主机表示我有几个从机我就开几条 SS所有从机一人一根都别抢我需要找你的时候我就控制接到你那一根的 SS 线给你低电平就说明我要找你了给你高电平就说明我不跟你玩了那这样一来指定从机不就是动动手指就能完成的事了么哪还需要什么分配地址先发一个字节寻址的操作啊。那这就是 SPI 实现一主多从指定从机的方式好处就是方便坏处就是得加钱线。 那最后这里SPI没有写应答机制的介绍SPI 没有应答机制的设计。发送数据就发送接收数据就接收至于对面是不是存在SPI 是不管的。
然后看一下下面的图片这些都是采用了 SPI 通信的芯片和模块。 第一个图就是我们本节使用的芯片型号是 W25Q64是一个 Flash 存储器这个模块的引脚可以看到和刚才说的并不一样。这里 CLK 就是 SCKDI 和 DO 就是 MOSI 和 MISO。那 DI 到底是 MOSI 还是 MISO 呢我们要看一下这个芯片的身份显然这个芯片接在 STM32 上应该是从机的身份所以这里的 DI数据输入就是从机的数据输入 SI对应需要接在主机的 MO 上所以这里的 DI 就是 MOSI那另一个 DO就是 MISO 了一般在这种始终作为从机的设备上可能会用 DI 和 DO 的简写。像 STM32 这种可以进行身份转换的设备一般都会把 MOSI、MISO 的全程写完整当然即使它简写了只要明确了它的身份是主机还是从机之后再辨别这两个引脚应该就好判断了。那最后一个 CS 片选其实就是 SS 从机选择了。
然后继续下一个模块这个是利用 SPI 通信的 OLED 屏幕上面的引脚也不是标准的名称所以这个模块要查一下手册在手册里有写的。
之后下一个这个是一个 2.4 G 无线通信模块芯片型号是 NRF24L01这个芯片使用的就是 SPI 通信协议要想使用这个芯片来进行无线通信那就需要利用 SPI来读写这个芯片。
然后最后一个图片就是常见的 Micro SD 卡了这个 SD 卡官方的通信协议是 SDIO但是它也是支持 SPI 协议的我们可以利用 SPI对这个 SD 卡进行读写操作。
那到这里我们这个 SPI 通信的大体介绍就完成了。
接下来我们来看一下 SPI 的硬件和软件规定。
1.2 SPI 硬件规定
所有SPI设备的SCK、MOSI、MISO分别连在一起主机另外引出多条SS控制线分别接到各从机的SS引脚输出引脚配置为推挽输出输入引脚配置为浮空或上拉输入
首先是硬件电路 这个图就是 SPI 一个典型的应用电路。我们看一下
左边这里是 SPI 主机主导整个 SPI 总线。主机一般都是控制器来作比如 STM32下面这里SPI 从机 1、2、3就是挂载在主机上的从设备了比如存储器、显示屏、通信模块、传感器等等等等。左边 SPI 主机实际上引出了 6 根通信线因为有 3 个从机所以 SS 线需要 3 根再加 SCK、MOSI、MISO就是 6 根通信线当然 SPI 所有通信线都是单端信号它们的高低电平都是相对 GND 的电压差。所以单端信号所有的设备还需要供电这里 GND 的线没画出来但是是必须要接的。然后如果从机没有独立供电的话主机还需要再额外引出电源正极 VCC给从机供电这两根电源线 VCC 和 GND也要注意接好。然后我们看一下这几根通信线首先SCK时钟线时钟线完全由主机掌控所以对于主机来说时钟线为输出对于所有从机来说时钟线都为输入这样主机的同步时钟就能送到各个从机了。然后下一个MOSI主机输出从机输入这里左边是主机所以就对应 MO主机输出下面三个都是从机所以就对应 SI从机输入数据传输方向是主机通过 MOSI 输出所有从机通过 MOSI 输入。接着下一个MISO主机输入从机输出左边是主机对应 MI下面三个都是从机对应 SO数据传输方向是三个从机通过 MISO 输出主机通过 MISO 输出。
那到这里SCK、MOSI、MISO 的连接方式我们就清楚了。这就是上面写的第一条所有SPI设备的SCK、MOSI、MISO分别连在一起就是上面图示的这样每条线的数据传输方向图中都用箭头标出来了可以看一下应该都挺明确的。
之后我们继续看时钟和数据传输没问题了。最后要解决的就是从机的选择问题了为了确定通信的目标主机就要另外引出多条 SS 通信线分别接到各从机的 SS 引脚上面图中有 3 个从机我们需要在主机另外引出 3 根 SS 选择线分别接到每个从机的 SS 输入端。主机的 SS 线都是输出从机的 SS 线都是输入SS 线是低电平有效的主机想指定谁就把对应的 SS 输出线置低电平就行了。比如主机初始化之后所有的 SS 都输出高电平这样就是谁也不指定。当主机需要和比如从机 1进行通信了主机就把 SS1 线输出低电平这样从机 1 就知道主机在找我然后主机在数据引脚进行的传输就只有从机 1 会响应其他从机的 SS 线是高电平所以它们都会保持沉默。当主机和从机 1 通信完成之后就会把 SS1 置回高电平这样从机 1 就知道主机结束了和我的通信。之后主机需要和从机 2 和从机 3 通信时也是同理需要找谁通信就置谁的 SS 为低电平。当然同一时间主机只能置一个 SS 为低电平只能选中一个从机否则如果主机同时选中多个从机就会导致数据冲突这就是 SPI 实现选择从机的方式。不需要像 I2C 一样进行寻址是不是挺简单的。
然后我们继续看下一条输出引脚配置为推挽输出输入引脚配置为浮空或上拉输入这就是 SPI 引脚的配置。在上图里输出引脚和输入引脚都用箭头标出来了哪个是输出哪个是输入应该很好判断。对于输出我们配置推挽输出推挽输出高低电平具有很强的驱动能力这将使得 SPI 引脚信号的下降沿非常迅速上升沿也非常迅速不像 I2C 那样下降沿非常迅速但是上升沿就比较缓慢了。那得益于推挽输出的驱动能力SPI 信号变化的快那自然它就能达到更高的传输速度一般 SPI 信号都能轻松达到 MHz 的速度级别。然后这里 I2C 并不是不想使用更快的推挽输出而是 I2C 要实现半双工经常要切换输入输出另外 I2C 又要实现多主机的时钟同步和总线仲裁这些功能都不允许 I2C 使用推挽输出要不然一不小心就电源短路了所以 I2C 选择了更多的功能自然就要放弃更强的性能了。对于 SPI 来说首先 SPI 不支持多主机然后 SPI 又是全双工SPI 的输出引脚始终是输出输入引脚始终是输入基本不会出现冲突所以 SPI 可以大胆地使用推挽输出。不过当然SPI 其实还是有一个冲突点的就是图上的 MISO 引脚在这个引脚上可以看到主机一个是输入但是三个从机全都是输出如果三个从机都始终是推挽输出势必会导致冲突。所以在 SPI 协议里有一条规定就是当从机的 SS 引脚为高电平也就是从机未被选中时它的 MISO 引脚必须切换为高阻态高阻态就相当于引脚断开不输出任何电平这样就可以防止一条线有多个输出而导致的电平冲突的问题了。在 SS 为低电平时MISO 才允许变为推挽输出这就是 SPI 对这个可能的冲突做出的规定当然这个切换过程都是在从机里我们一般都是写主机的程序所以我们主机的程序中并不需要关注这个问题。
好那有关 SPI 的硬件电路就介绍到这里。
接下来我们来看一下移位示意图 这个移位示意图是 SPI 硬件电路设计的核心。只要你把这个移位示意图搞懂了那无论是上面的硬件电路还是我们等会学习的软件时序理解起来都会更加轻松。我们看一下
SPI 的基本收发电路就是使用了这样一个移位的模型
1.3 SPI 软件规定