一、概述
对于嵌入式通用MCU来说,SPI作为从机的应用相比作为主机来说比较少,网络上无论是哪个品牌的MCU,对于SPI从机的介绍以及性能也是比较少。
先楫在SPI外设上,单从hpm_sdk上看,SPI外设的每个sample例子,比如poll方式、中断方式、DMA方式的例子都有对应的主机和从机例子,相对应提供了SPI主机和从机的操作方式。
本文就从hpm_sdk的spi sample例子入手,对于poll和中断方式本文不阐述,若需要了解差异可看该系列文章的SPI主机说明部分。
本文以spi的sample中的DMA例子来进行阐述,硬件上需要两块HPM的板子,比如两块hpm6200evk。以此来说明SPI从机发送和接收的性能。
二、HPM_SDK的SPI从机相关API介绍
SPI外设的大多API接口都可适用于SPI主机或者从机,本文主要介绍SPI从机需要的API接口
(一) SPI从机的功能时钟开启
hpm_sdk中,每个芯片的官方板子,也就是对应的board文件,比如hpm6200evk的board.c,里面包含了board_init_spi_clock这API,里面实现了SPI的时钟指向group以及时钟的来源。
可以看到,SPI时钟来源于PLL时钟的PLL0_CLK--400M,经过五分频得到的,也就是80M。本文就是基于这个SPI工作频率下进行验证。
需要说明的是:SPI作为从机的时候,对应的SPI主机设备驱动输出的SCK时钟必须小于等于SPI工作频率的1/4,也就是20M的SPI SCLK驱动。
(二)SPI从机的两种数据传输模式
SPI作为从机,对于数据的传输分为两种:纯数据模式和非纯数据模式。这个设置位在TRANSCTRL中的SLVDATAONLY位域。
那么何为纯数据模式呢,在UM手册可以看到SPI控制器对于SPI从机的介绍:
SPI作为从机模式下,如果不配置SLVDATAONLY这个位域,那么默认就是0,也就是控制器会把SPI总线上的信号,分别解释为命令、等待和数据。而且命令和等待段都是固定为8位。
这也就是说,非纯数据模式下,SPI从机在收到SCLK开始,前面的头16个时钟周期,也就是8个字节,会被从机认为是命令、等待段,其余的才是数据段。
这样就好理解纯数据模式下是什么意思了,纯数据模式下,SPI作为从机时,SPI控制器会把SPI总线上的所有信号都解释为数据段。
需要注意的是,在纯数据模式下,SPI传输模式只能同时读写模式,同时也只能用于常规模式(1线模式)。
可以做个实验验证下,在保持SPI DMA的master sample保持不变,也就是SPI主机会发命令和地址段。在SPI从机看来就是命令和地址段。
当为非纯数据模式下时,SPI从机的数据段不会带有SPI主机发过来的命令和地址字节。
当为纯数据模式下,SPI从机会把SPI总线上的所有数据识别为数据段。
对应的API接口可以在spi_control_config_t结构体里面的spi_slave_control_config_t结构体
对应赋值API接口主要有传输API和SPI控制配置初始化
在进行配置传输的时候,比如spi_setup_dma_transfer 这个DMA方式的API,这个API在SPI作为从机上,主要调用了上面的spi_control_init API对SPI的TRANSCTRL寄存器进行配置,主要就是配置数据传输是否为纯数据模式,以及SPI传输模式、然后开启接收或者发送DMA。
开发者使用该API,只需要赋值对应的结构体成员,然后进行调用。比如本文使用的SPI DMA中的SPI slave 这个例子.。
配置好SPI之后,需要配置下DMA,比如DMA的源地址和设备地址等等。之后等待从机的收发数据计数是否到了配置TRANSCTRL寄存器的收发长度。
对应的API为spi_slave_get_sent_data_count 和 spi_slave_get_received_data_count 两个API
详情的流程可以参考hpm_sdk中的sample/drivers/spi/dma的代码。
三、SPI从机收发性能验证
SPI的功能时钟,手册中写的是80M,SPI作为从机的时候,SPI总线的频率时钟不能大于四分之一SPI功能时钟,也就是20M的SPI SCLK时钟。
需要注意的是:测试收发的数据要放在AHB SRAM当中。
(一)SPI 20M SCLK时钟驱动符合手册预期
sample的例子也是基于20M进行验证。下载之后查看双板log以及示波器,可以看到SPI总线的SCK时钟保持连续,并且双板通信收发正常。
在SPI 25M SCLK时钟驱动依旧收发正常。
(二)SPI 25M以上 SCLK时钟驱动数据收发不正常 (根据自己应用进行小技巧纠正)
在手册规定下的SPI总线20M的时钟下,对于SPI从机来说,25M以下的频率,SPI从机还能来得及采样。但一旦超过25M之后,SPI从机对于总线上的数据,由于来不及采样,导致可能会出现第一位或者第二位出现丢失导致数据收发异常,从而导致数据接收左移。
比如在SPI总线40M SCLK情况下,会遇到由于SPI从机没采样到第一位,导致后续的数据位全部左移一位。
sdk的sample使用的SPI模式是模式3,也就是总线空闲时是高电平,第1个跳变沿是下降沿,第2个跳变沿是上升沿,数据在第2个跳变沿(上升沿)采样。
1、从机接收纠正小技巧
从机的SCLK时钟由主机提供,接收主机的数据的时候,所以无论是哪种方式,都会由于采样速度慢于主机的原因,延后一个或者两个的采样位,导致数据产生偏移。那么软件上可以通过偏移的采样位进行右移得到正确的数据,比如从机收到的是0x02,采样位偏移1位,那么右移可以得到0x01。则正确对上数据。
SCK的时钟阴影部分表示从机丢失的时钟采样。
2、从机发送纠正小技巧
跟上面同样的原理,由于主机采样比从机快,所以不存在数据左移的情况。那么从机的SPI模式可以改成跟主机的SPI模式相反。
比如主机的SPI模式是模式3,也就是总线空闲时是高电平,第1个跳变沿是下降沿,第2个跳变沿是上升沿,数据在第2个跳变沿(上升沿)采样。
而从机可以配置为模式0,也就是空闲时是低电平,第1个跳变沿是上升沿,第2个跳变沿是下降沿,数据在第1个跳变沿(上升沿)采样。
SCK的时钟阴影部分表示从机丢失的时钟采样。
例子可以这么改动。
编译后烧录,SPI主机从机的发送和接收,可以看到:
SPI主机发送给SPI从机的数据,从机显示总会左移一位。可以通过软件处理偏移,但不推荐。
而SPI从机发给SPI主机,由于双方的模式相反,根据上述阐述,主机收到的数据跟从机发送的一样。
四、总结
1、先楫在SPI从机功能时钟为80M下,从机收发可以达到20M到25M左右,单线SPI可以2.5MB/s左右速度。达到这符合官方手册说明。
2、可以通过提升SPI功能时钟提升从机收发性能,但不保证功能是否正常,不在本文和官方手册阐述范围内。
3、由于再高的SPI SCLK,会导致从机时序采样过慢导致数据收发异常,如果想继续提升从机的收发性能,可以通过一些小技巧来避免时序错位的问题。但这些小技巧取决于自己的应用,不在官方手册阐述范围内。