SPI简介
https://zhuanlan.zhihu.com/p/150121520
SPI要用到四个管脚分别是使能管脚cs、时钟管脚sck、mosi管脚(主机输出从机输入)有时也叫SDO、miso管脚(主机输入从机输出管脚)又叫SDI;
配置过程
1、开启GPIOB的时钟、开启spi的时钟
2、配置gpio口,cs通用推挽输出、sck和mosi服用推挽输出、miso浮空输入
3、配置SPI
4、使能spi
//CS-PB12 SCK-PB13 MISO-PB14 MOSI-PB15
//SPI2
void SPI_Config(void)
{
GPIO_InitTypeDef GPIO_InitStruct={0};
SPI_InitTypeDef SPI_InitStruct={0};
//1,开时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_SPI2,ENABLE);
//2,配置IO口
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;//复用推挽
GPIO_InitStruct.GPIO_Pin = GPIO_Pin_13|GPIO_Pin_15;
GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB,&GPIO_InitStruct);
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空输入
GPIO_InitStruct.GPIO_Pin = GPIO_Pin_14;
GPIO_Init(GPIOB,&GPIO_InitStruct);
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;//通用推挽输出
GPIO_InitStruct.GPIO_Pin = GPIO_Pin_12;
GPIO_Init(GPIOB,&GPIO_InitStruct);
GPIO_SetBits(GPIOB,GPIO_Pin_12);//先拉高,避免误操作
//3,SPI配置 模式0 参数完全根据从机来定
SPI_InitStruct.SPI_BaudRatePrescaler=SPI_BaudRatePrescaler_2;//通信时钟速度
SPI_InitStruct.SPI_CPHA=SPI_CPHA_1Edge;//时钟相位
SPI_InitStruct.SPI_CPOL=SPI_CPOL_Low;//时钟极性
SPI_InitStruct.SPI_CRCPolynomial=0x7;//从设备不支持CRC,可以忽略
SPI_InitStruct.SPI_DataSize=SPI_DataSize_8b;//数据宽度
SPI_InitStruct.SPI_Direction=SPI_Direction_2Lines_FullDuplex;//两线全双工
SPI_InitStruct.SPI_FirstBit=SPI_FirstBit_MSB;//高位先传
SPI_InitStruct.SPI_Mode=SPI_Mode_Master;//主模式
SPI_InitStruct.SPI_NSS=SPI_NSS_Soft;//软件管理,普通IO口代替
SPI_Init(SPI2,&SPI_InitStruct);
//4,SPI使能
SPI_Cmd(SPI2,ENABLE);
}
发送接收函数
要想读取从机一个数据必须先发送一个数据给从机然后从机才会返还给你一个数据
//SPI发送接收函数
uint8_t SPI_Senddata(uint8_t data)
{
uint8_t recv = 0;
//等待发送完成
while(SPI_I2S_GetFlagStatus(SPI2,SPI_I2S_FLAG_TXE)!= SET);
SPI_I2S_SendData(SPI2,data);
//等待接收标志置位
while(SPI_I2S_GetFlagStatus(SPI2,SPI_I2S_FLAG_RXNE)!= SET);
recv = SPI_I2S_ReceiveData(SPI2);
return recv;
}