STM32F091 SPI DMA Problem
Hello,
I try to read acceleration values from a LIS3DSHTR using the STM32F091 �C. I use SPI with DMA to read the values but I have trouble with the incoming datas in the RxBuffer.
On my two screenshots you can see the bus communication and the position of the data inside my RxBuffer. The order is totally wrong.
I hope someone can check the source code. I hope you can find a stupid mistake
void SPI_init()
{ SPI_InitTypeDef SPI_InitStructure;// clk
RCC->AHBENR |= RCC_AHBENR_GPIOAEN; RCC->APB2ENR |= RCC_APB2ENR_SPI1EN;// set af mode
GPIOA->MODER = ( GPIOA->MODER & ~(GPIO_MODER_MODER5 | GPIO_MODER_MODER6 | GPIO_MODER_MODER7)); GPIOA->MODER |= ( GPIO_MODER_MODER5_1 | GPIO_MODER_MODER6_1 | GPIO_MODER_MODER7_1);GPIOA->AFR[1] = (GPIOA->AFR[1] &~ (GPIO_AFRL_AFR5)) | (0 << GPIO_AFR_POS5);
GPIOA->AFR[1] = (GPIOA->AFR[1] &~ (GPIO_AFRL_AFR6)) | (0 << GPIO_AFR_POS6); GPIOA->AFR[1] = (GPIOA->AFR[1] &~ (GPIO_AFRL_AFR7)) | (0 << GPIO_AFR_POS7);SPIx_PORT->MODER |= ( GPIO_MODER_MODER4_0);
SPIx_PORT->OTYPER &= ~( GPIO_OTYPER_OT_4); SPIx_PORT->OSPEEDR |= ( GPIO_OSPEEDER_OSPEEDR4); SPIx_PORT->PUPDR &= ~( GPIO_PUPDR_PUPDR4);SPIx_PORT->BSRR = GPIO_BSRR_BS_4; //High - Deselect ACC
/*SPI1-Konfigurieren*/
SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex; SPI_InitStructure.SPI_Mode = SPI_Mode_Master; SPI_InitStructure.SPI_DataSize = SPI_DataSize_8b; 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_MSB; SPI_InitStructure.SPI_CRCPolynomial = 7; SPI_Init(SPIx,&SPI_InitStructure);//Use DMA for SPI
SPI_I2S_DMACmd(SPIx, SPI_I2S_DMAReq_Tx, ENABLE); SPI_I2S_DMACmd(SPIx, SPI_I2S_DMAReq_Rx, ENABLE);SPI_Cmd(SPIx, ENABLE);
//Init DMA
DMA_Config();//Init the buffer with the needed registers of the acc
AccelerationRequest[0] = ACCELEROMETER_OUT_X_L; AccelerationRequest[1] = 0x00; //dummy AccelerationRequest[2] = ACCELEROMETER_OUT_X_H; AccelerationRequest[3] = 0x00; AccelerationRequest[4] = ACCELEROMETER_OUT_Y_L; AccelerationRequest[5] = 0x00; AccelerationRequest[6] = ACCELEROMETER_OUT_Y_H; AccelerationRequest[7] = 0x00; AccelerationRequest[8] = ACCELEROMETER_OUT_Z_L; AccelerationRequest[9] = 0x00; AccelerationRequest[10] = ACCELEROMETER_OUT_Z_H; AccelerationRequest[11] = 0x00;}void DMA_Config()
{ DMA_InitTypeDef DMA_InitStructure; NVIC_InitTypeDef NVIC_InitStructure;DMA_DeInit(DMA1_Channel2);
DMA_DeInit(DMA1_Channel3);DMA_StructInit(&DMA_InitStructure);
// Enable DMA1 Peripheral Clock (SPI_DECAWAVE and SPI_BUS)
RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);// Configure SPI_BUS RX Channel
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC; // From SPI to memory DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)&SPI1->DR; DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte; DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)RxBuffer; DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte; DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable; DMA_InitStructure.DMA_BufferSize = sizeof(RxBuffer); DMA_InitStructure.DMA_Mode = DMA_Mode_Normal; DMA_InitStructure.DMA_Priority = DMA_Priority_High; DMA_InitStructure.DMA_M2M = DMA_M2M_Disable; DMA_Init(DMA1_Channel2, &DMA_InitStructure);// Configure SPI_BUS TX Channel
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralDST; // From memory to SPI DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)&SPI1->DR; DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte; DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)TxBuffer; DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte; DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable; DMA_InitStructure.DMA_BufferSize = sizeof(TxBuffer);; DMA_InitStructure.DMA_Mode = DMA_Mode_Normal; DMA_InitStructure.DMA_Priority = DMA_Priority_High; DMA_InitStructure.DMA_M2M = DMA_M2M_Disable; DMA_Init(DMA1_Channel3, &DMA_InitStructure);DMA_ITConfig(DMA1_Channel2, DMA_IT_TC, ENABLE);
NVIC_InitStructure.NVIC_IRQChannel = DMA1_Channel2_3_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPriority = 0; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure);}//ReadAddrBuffer = AccelerationRequest with the Register values + DummyByte, Size = 12
void SPI_ReadRegisters(uint8_t* ReadAddrBuffer, uint8_t Size){ for (uint8_t i=0; i < Size; i++) { if (ReadAddrBuffer[i] > 0x00) TxBuffer[i] = ReadAddrBuffer[i] | READ_FLAG; else TxBuffer[i] = 0x00; }DMA_Cmd(DMA1_Channel2, DISABLE);
DMA_Cmd(DMA1_Channel3, DISABLE);DMA_SetCurrDataCounter(DMA1_Channel2, Size);
DMA_SetCurrDataCounter(DMA1_Channel3, Size);SPI_SelectChip();
DMA_Cmd(DMA1_Channel2, ENABLE);
DMA_Cmd(DMA1_Channel3, ENABLE);}void DMA1_Channel2_3_IRQHandler(void){ if (DMA_GetITStatus(DMA1_IT_TC2) != RESET) { SPI_DeselectChip();int16_t x = (int16_t)((RxBuffer[1] << 8) | RxBuffer[0]); // / 16384.0f;
int16_t y = (int16_t)((RxBuffer[3] << 8) | RxBuffer[2]); // / 16384.0f; int16_t z = (int16_t)((RxBuffer[5] << 8) | RxBuffer[4]); // / 16384.0f;DMA_ClearFlag(DMA1_FLAG_TC2);
}}#stm32 #accelerometer #dma #spi