Files
2024-09-18 11:50:26 +08:00

163 lines
4.5 KiB
C
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/*
* drv_spi.c
*
* Created on: Jun 28, 2023
* Author: gxms0
*/
#include "drv_spi.h"
void spi_init(SPI_ptr ptr)
{
}
void spi_config(SPI_ptr ptr, SPI_TypeDef *SPI, GPIO_TypeDef *GPIO_MOSI, uint32_t Pin_MOSI, GPIO_TypeDef *GPIO_MISO, uint32_t Pin_MISO, GPIO_TypeDef *GPIO_SCK, uint32_t Pin_SCK,
uint32_t GPIO_Remap)
{
GPIO_InitTypeDef GPIO_InitStructure = {0};
SPI_InitTypeDef SPI_InitStructure={0};
DMA_InitTypeDef DMA_InitStructure = {0};
NVIC_InitTypeDef NVIC_InitStructure = {0};
uint32_t RCC_Periph = RCC_APB2Periph_SPI1;
ptr->SPI = SPI;
ptr->GPIO_MOSI = GPIO_MOSI;
ptr->GPIO_MISO = GPIO_MISO;
ptr->GPIO_SCK = GPIO_SCK;
ptr->Pin_MOSI = Pin_MOSI;
ptr->Pin_MISO = Pin_MISO;
ptr->Pin_SCK = Pin_SCK;
RCC_APB2PeriphClockCmd( RCC_APB2Periph_AFIO, ENABLE );
if(ptr->SPI == SPI1){RCC_Periph = RCC_APB2Periph_SPI1;RCC_APB2PeriphClockCmd(RCC_Periph, ENABLE);}
else if(ptr->SPI == SPI2){RCC_Periph = RCC_APB1Periph_SPI2;RCC_APB1PeriphClockCmd(RCC_Periph, ENABLE);}
//初始化IO口
//init mosi
if(ptr->GPIO_MOSI == GPIOA)RCC_Periph = RCC_APB2Periph_GPIOA;
else if(ptr->GPIO_MOSI == GPIOB)RCC_Periph = RCC_APB2Periph_GPIOB;
else if(ptr->GPIO_MOSI == GPIOC)RCC_Periph = RCC_APB2Periph_GPIOC;
else if(ptr->GPIO_MOSI == GPIOD)RCC_Periph = RCC_APB2Periph_GPIOD;
else if(ptr->GPIO_MOSI == GPIOE)RCC_Periph = RCC_APB2Periph_GPIOE;
RCC_APB2PeriphClockCmd(RCC_Periph, ENABLE);
GPIO_InitStructure.GPIO_Pin = ptr->Pin_MOSI;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(ptr->GPIO_MOSI, &GPIO_InitStructure);
//init miso
if(ptr->GPIO_MISO == GPIOA)RCC_Periph = RCC_APB2Periph_GPIOA;
else if(ptr->GPIO_MISO == GPIOB)RCC_Periph = RCC_APB2Periph_GPIOB;
else if(ptr->GPIO_MISO == GPIOC)RCC_Periph = RCC_APB2Periph_GPIOC;
else if(ptr->GPIO_MISO == GPIOD)RCC_Periph = RCC_APB2Periph_GPIOD;
else if(ptr->GPIO_MISO == GPIOE)RCC_Periph = RCC_APB2Periph_GPIOE;
RCC_APB2PeriphClockCmd(RCC_Periph, ENABLE);
GPIO_InitStructure.GPIO_Pin = ptr->Pin_MISO;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(ptr->GPIO_MISO, &GPIO_InitStructure);
//init sck
if(ptr->GPIO_SCK == GPIOA)RCC_Periph = RCC_APB2Periph_GPIOA;
else if(ptr->GPIO_SCK == GPIOB)RCC_Periph = RCC_APB2Periph_GPIOB;
else if(ptr->GPIO_SCK == GPIOC)RCC_Periph = RCC_APB2Periph_GPIOC;
else if(ptr->GPIO_SCK == GPIOD)RCC_Periph = RCC_APB2Periph_GPIOD;
else if(ptr->GPIO_SCK == GPIOE)RCC_Periph = RCC_APB2Periph_GPIOE;
RCC_APB2PeriphClockCmd(RCC_Periph, ENABLE);
GPIO_InitStructure.GPIO_Pin = ptr->Pin_SCK;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(ptr->GPIO_SCK, &GPIO_InitStructure);
//init peripheral
SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex;
SPI_InitStructure.SPI_Mode = SPI_Mode_Master;
SPI_InitStructure.SPI_DataSize = SPI_DataSize_16b;
SPI_InitStructure.SPI_CPOL = SPI_CPOL_Low;
SPI_InitStructure.SPI_CPHA = SPI_CPHA_1Edge;
SPI_InitStructure.SPI_NSS = SPI_NSS_Soft;
SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_64;
SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_LSB;
SPI_InitStructure.SPI_CRCPolynomial = 7;
SPI_Init( ptr->SPI, &SPI_InitStructure );
//init dma
//init nvic
uint8_t NVIC_IRQChannel = USART1_IRQn;
if(ptr->SPI == SPI1)NVIC_IRQChannel = SPI1_IRQn;
else if(ptr->SPI == SPI2)NVIC_IRQChannel = SPI2_IRQn;
NVIC_InitStructure.NVIC_IRQChannel = NVIC_IRQChannel;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
SPI_I2S_ITConfig(ptr->SPI, SPI_I2S_IT_RXNE, ENABLE);//读取数据,收到数据
//SPI_I2S_ITConfig(ptr->SPI, SPI_I2S_IT_IDLE, ENABLE);//读取整包数据(读取fifo
SPI_I2S_ITConfig(ptr->SPI, SPI_I2S_IT_TXE, DISABLE);//发送可以不开中断,只要传到dma即可
SPI_Cmd( ptr->SPI, ENABLE );
}
//SPI读写比较特殊,用到再说
void spi_read(SPI_ptr ptr,unsigned char *buff,const unsigned int len)
{
//数字长于2字节就用 DMA,IT,数字短就用阻塞模式
}
void spi_write(SPI_ptr ptr,const unsigned char *buff,const unsigned int len)
{
GPIO_WriteBit(ptr->GPIO_CS, ptr->Pin_CS, Bit_RESET);
GPIO_WriteBit(ptr->GPIO_CS, ptr->Pin_CS, Bit_SET);
}