cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F373 SPI3 DMA data exchange

megahercas6
Senior
Posted on May 12, 2015 at 11:01

Hello,

I am working on simple project, where i need to exchange data with other microcontroller, but it would be better to use DMA for it in circular mode. I had this program working without a glitch on STM32F4 part, but no luck with STM32F373 part. As far as my understanding goes, if i select circular mode and use SPI as master, i should get constant data flow from SPI. If i run this code, and using software spi commands like while(!SPI_I2S_GetFlagStatus(SPI3, SPI_I2S_FLAG_TXE)); SPI_I2S_SendData16(SPI3,(x)); I get data on output, so it looks like at least SPI part is working, but DMA not

#define SPIx_TX_DMA_CHANNEL DMA2_Channel2
#define SPIx_RX_DMA_CHANNEL DMA2_Channel1
#define SPI_DMAx_CLK RCC_AHBPeriph_DMA2
#define SPIx SPI3
#define SPIx_CLK RCC_APB1Periph_SPI3
#define SPIx_SCK_PIN GPIO_Pin_3
#define SPIx_SCK_GPIO_PORT GPIOB
#define SPIx_SCK_GPIO_CLK RCC_AHBPeriph_GPIOB
#define SPIx_SCK_SOURCE GPIO_PinSource3
#define SPIx_SCK_AF GPIO_AF_6
#define SPIx_MISO_PIN GPIO_Pin_4
#define SPIx_MISO_GPIO_PORT GPIOB
#define SPIx_MISO_GPIO_CLK RCC_AHBPeriph_GPIOB
#define SPIx_MISO_SOURCE GPIO_PinSource4
#define SPIx_MISO_AF GPIO_AF_6
#define SPIx_MOSI_PIN GPIO_Pin_5
#define SPIx_MOSI_GPIO_PORT GPIOB
#define SPIx_MOSI_GPIO_CLK RCC_AHBPeriph_GPIOB
#define SPIx_MOSI_SOURCE GPIO_PinSource5
#define SPIx_MOSI_AF GPIO_AF_6
void SPI_DMA_Config(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
SPI_InitTypeDef SPI_InitStructure;
DMA_InitTypeDef DMA_InitStructure;
/* Enable the SPI peripheral */
RCC_APB1PeriphClockCmd(SPIx_CLK, ENABLE);
RCC_AHBPeriphClockCmd(SPIx_SCK_GPIO_CLK | SPIx_MISO_GPIO_CLK | SPIx_MOSI_GPIO_CLK, ENABLE);
RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA2, ENABLE);
/* SPI pin mappings */
GPIO_PinAFConfig(SPIx_SCK_GPIO_PORT, SPIx_SCK_SOURCE, SPIx_SCK_AF);
GPIO_PinAFConfig(SPIx_MOSI_GPIO_PORT, SPIx_MOSI_SOURCE, SPIx_MOSI_AF);
GPIO_PinAFConfig(SPIx_MISO_GPIO_PORT, SPIx_MISO_SOURCE, SPIx_MISO_AF);
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_DOWN;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
/* SPI SCK pin configuration */
GPIO_InitStructure.GPIO_Pin = SPIx_SCK_PIN;
GPIO_Init(SPIx_SCK_GPIO_PORT, &GPIO_InitStructure);
/* SPI MOSI pin configuration */
GPIO_InitStructure.GPIO_Pin = SPIx_MOSI_PIN;
GPIO_Init(SPIx_MOSI_GPIO_PORT, &GPIO_InitStructure);
/* SPI MISO pin configuration */
GPIO_InitStructure.GPIO_Pin = SPIx_MISO_PIN;
GPIO_Init(SPIx_MISO_GPIO_PORT, &GPIO_InitStructure);
/* SPI configuration -------------------------------------------------------*/
SPI_I2S_DeInit(SPIx);
SPI_InitStructure.SPI_Mode = SPI_Mode_Master;//SPI_Mode_Slave;//
SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex;
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_8;
SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB;
SPI_InitStructure.SPI_CRCPolynomial = 7;
SPI_Init(SPIx, &SPI_InitStructure);
/* DMA Configuration -------------------------------------------------------*/
DMA_InitStructure.DMA_PeripheralDataSize = DMA_MemoryDataSize_HalfWord;//DMA_PeripheralDataSize_Byte;
DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;//DMA_MemoryDataSize_Byte;
DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;
DMA_InitStructure.DMA_M2M = DMA_M2M_Disable; 
/* DMA channel Rx of SPI Configuration */
DMA_InitStructure.DMA_BufferSize = (uint16_t)7;
DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t) (&(SPI3->DR));
DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)RxData;
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;
DMA_InitStructure.DMA_Priority = DMA_Priority_High;
DMA_Init(SPIx_RX_DMA_CHANNEL, &DMA_InitStructure);
/* DMA channel Tx of SPI Configuration */
DMA_InitStructure.DMA_BufferSize = (uint16_t)7;
DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t) (&(SPI3->DR));
DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)TxData;
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralDST;
DMA_InitStructure.DMA_Priority = DMA_Priority_Low;
DMA_Init(SPIx_TX_DMA_CHANNEL, &DMA_InitStructure);
DMA_ClearFlag(DMA2_FLAG_GL1);
DMA_ClearFlag(DMA2_FLAG_GL2);
/* Enable the SPI Rx and Tx DMA requests */
SPI_I2S_DMACmd(SPIx, SPI_I2S_DMAReq_Rx, ENABLE);
SPI_I2S_DMACmd(SPIx, SPI_I2S_DMAReq_Tx, ENABLE);
/* Enable the SPI peripheral */
SPI_Cmd(SPIx, ENABLE);
DMA_Cmd(SPIx_RX_DMA_CHANNEL, ENABLE);
DMA_Cmd(SPIx_TX_DMA_CHANNEL, ENABLE);
DMA_ITConfig(DMA2_Channel1,DMA_IT_TC, ENABLE);
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);
NVIC_InitTypeDef NVIC_InitStruct;
NVIC_InitStruct.NVIC_IRQChannel = DMA2_Channel1_IRQn;
NVIC_InitStruct.NVIC_IRQChannelCmd = ENABLE;
NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority = 1;
NVIC_InitStruct.NVIC_IRQChannelSubPriority = 0;
NVIC_Init(&NVIC_InitStruct);
}

Could any one spot the possible problem ? Its third day with no progress, and i am starting to regret to use STM32F373 part, since with STM32F4 it will be working in few minutes
2 REPLIES 2
Posted on May 12, 2015 at 11:23

Looks reasonable at the first glance, but you might want to read the relevant registers in SPI and DMA in the debugger and check whether they are set correctly.

JW

megahercas6
Senior
Posted on May 12, 2015 at 12:16

Hi,

Well, what do you know, cross checking DMA registers showed problem. & was missing indicating address.

Thanks for the tip ( I am still using bad approach for problem solving, i usually referencing my work with examples, not registers inside reference manual, sometimes it works faster, but this approach is not a way to go)