SPI(Serial Peripheral Interface)总线
串行外设接口 (SPI) 是同步串行通信的事实上的标准(有许多变体),主要用于嵌入式系统中集成电路之间的短距离有线通信。
SPI 使用主-子节点(主/从)架构,其中一个主设备通过提供控制任意数量从属外设的时钟信号和片选信号来协调通信。
摩托罗拉的原始规格使用四根线来执行全双工通信。 它有时被称为四线串行总线,以与半双工的三线变体以及两线 I²C 和 1-Wire 串行总线形成对比。
典型应用包括将微控制器与安全数字卡、液晶显示器、模数和数模转换器、闪存和 EEPROM 存储器以及各种通信芯片的外围芯片连接起来。
SPI 可以准确地描述为同步串行接口,但它不同于同步串行接口 (SSI) 协议。
HXDSP2441 SPI
HXDSP2441在BSP中提供的SPI裸机驱动接口具体查询《HXDSP2441裸机驱动用户手册》4.4。需要特别说明的是,因为BSP内提供的所有SPI相关接口均针对Flash器件,如果SPI所控为非Flash器件,则需要仔细阅读BSP源码并在必要时重新实现驱动接口。由于Demo板通过SPI接口控制ADC器件(MAX11635),所以对BSP的SPI相关源码进行修改,以下涉及源码文件均在BSP包的drivers/spi/文件夹下。
以spi_write接口为例,分析其调用路径:
spi_write传入spi_bus结构体,最终由resolve_command函数解析结构体成员spi_bus.spi_message.flag进而确认SPI操作Flash的命令字,原本flag为SPI_WRITE时对应写flash_readwrite的写功能,将flash_readwrite对应改为我自己实现的spi_readwrite函数,spi_read接口同理,spi_readwrite函数实现如下(spi_readwrite接口并不需要device_type,只为与原有接口保持一致)。
/*
*功能:SPI RAW 读写
*参数:总线结构
*/
spi_status_code spi_readwrite(spi_bus *bus,uint32_t device_type){
uint64_t base = bus->base;
uint32_t status = 0;
/*
* 写入的字节数
*/
int count = bus->msg->len;
/*
* 写入的缓冲区
*/
uint8_t *wbuf = bus->msg->buf;
uint8_t *rbuf = bus->msg->buf;
epos_interrupt_disable(0);
uint32_t fake_data = 0;
uint32_t tx_cnt=0, rx_cnt=0;
for(;tx_cnt<count || rx_cnt < count;){
status = *((volatile uint32_t*)base + SSI_SR_OFFSET);
if((tx_cnt<count) && (status & SR_TFNF)){
*((volatile uint32_t*)base + SSI_DR_OFFSET) = wbuf[tx_cnt];
tx_cnt++;
}
if((rx_cnt < count) && (status & SR_RFNE)){
rbuf[rx_cnt] = *((volatile uint32_t*)base + SSI_DR_OFFSET);
rx_cnt++;
}
}
wait_spi_completion(base);
epos_interrupt_enable(0);
return SPI_SUCCESSFUL;
}