2021-04-26 08:40 PM
I use tim dma burst to update CCRx(x=1\2\3\4),my code works,but the CCRx value not assigned in correct sequence. My purpose is to let CCR1= 360�?CCR2= 720�?CCR3=1080.
But the result are random.TIM and DMA config codes
void tim_config()
{
uint32_t address = 0;
uint16_t i =0;
for(i=0;i<80;i++)
{
uint16_t v = 0;
v = (i%4)*10;
dmaCCBuf[i] = 36*(v+10);
}
LL_AHB1_GRP1_EnableClock(LL_AHB1_GRP1_PERIPH_DMA1);
address = TIM1_DMAR_ADDRESS;
LL_DMA_ConfigAddresses(DMA1, LL_DMA_CHANNEL_5, (uint32_t)dmaCCBuf, address, LL_DMA_DIRECTION_MEMORY_TO_PERIPH);
LL_DMA_SetDataTransferDirection(DMA1, LL_DMA_CHANNEL_5, LL_DMA_DIRECTION_MEMORY_TO_PERIPH);
LL_DMA_SetDataLength(DMA1, LL_DMA_CHANNEL_5, 4);
LL_DMA_SetMemoryIncMode(DMA1, LL_DMA_CHANNEL_5, LL_DMA_MEMORY_INCREMENT);
LL_DMA_SetPeriphIncMode(DMA1, LL_DMA_CHANNEL_5, LL_DMA_PERIPH_NOINCREMENT);
LL_DMA_SetMode(DMA1, LL_DMA_CHANNEL_5, LL_DMA_MODE_NORMAL);//
LL_DMA_SetChannelPriorityLevel(DMA1, LL_DMA_CHANNEL_5, LL_DMA_PRIORITY_VERYHIGH);
LL_DMA_SetPeriphSize(DMA1, LL_DMA_CHANNEL_5, LL_DMA_PDATAALIGN_HALFWORD);
LL_DMA_SetMemorySize(DMA1, LL_DMA_CHANNEL_5, LL_DMA_MDATAALIGN_HALFWORD);
LL_TIM_ConfigDMABurst(TIM1, LL_TIM_DMABURST_BASEADDR_CCR1, LL_TIM_DMABURST_LENGTH_4TRANSFERS);
LL_TIM_EnableDMAReq_UPDATE(TIM1);
LL_TIM_EnableIT_UPDATE(TIM1);
LL_TIM_CC_EnableChannel(TIM1, LL_TIM_CHANNEL_CH1);
LL_TIM_CC_EnableChannel(TIM1, LL_TIM_CHANNEL_CH1N);
LL_TIM_CC_EnableChannel(TIM1, LL_TIM_CHANNEL_CH2);
LL_TIM_CC_EnableChannel(TIM1, LL_TIM_CHANNEL_CH2N);
LL_TIM_CC_EnableChannel(TIM1, LL_TIM_CHANNEL_CH3);
LL_TIM_CC_EnableChannel(TIM1, LL_TIM_CHANNEL_CH3N);
LL_TIM_CC_EnableChannel(TIM1, LL_TIM_CHANNEL_CH4);
LL_TIM_SetTriggerOutput(TIM1, LL_TIM_TRGO_OC4REF);
//LL_TIM_SetTriggerOutput(TIM1, LL_TIM_TRGO_UPDATE);
LL_TIM_EnableARRPreload(TIM1);
LL_TIM_OC_DisablePreload(TIM1, LL_TIM_CHANNEL_CH1);
LL_TIM_OC_DisablePreload(TIM1, LL_TIM_CHANNEL_CH2);
LL_TIM_OC_DisablePreload(TIM1, LL_TIM_CHANNEL_CH3);
LL_TIM_OC_DisablePreload(TIM1, LL_TIM_CHANNEL_CH4);
LL_DMA_EnableIT_TC(DMA1, LL_DMA_CHANNEL_5);
LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_5);
NVIC_SetPriority(DMA1_Channel5_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),0, 0));
NVIC_EnableIRQ(DMA1_Channel5_IRQn);
LL_TIM_EnableCounter(TIM1);
}
DMA Interupt to restart once transfer
/* USER CODE BEGIN 1 */
void DMA1_Channel5_IRQHandler(void)
{
LL_GPIO_SetOutputPin(GPIOC, LL_GPIO_PIN_12);
LL_GPIO_ResetOutputPin(GPIOC, LL_GPIO_PIN_12);
if(LL_DMA_IsActiveFlag_TC5(DMA1))
{
LL_DMA_ClearFlag_TC5(DMA1);
LL_DMA_DisableChannel(DMA1, LL_DMA_CHANNEL_5);
LL_DMA_SetDataLength(DMA1, LL_DMA_CHANNEL_5, 4);
LL_DMA_EnableChannel(DMA1, LL_DMA_CHANNEL_5);
sFlag = 1;
}
}
Solved! Go to Solution.
2021-04-26 10:26 PM
Don't observe TIMx_DMAR in debugger. Debugger is intrusive and reading DMAR in it advanced the internal counter/pointer to the individual TIM registers.
JW
2021-04-26 10:26 PM
Don't observe TIMx_DMAR in debugger. Debugger is intrusive and reading DMAR in it advanced the internal counter/pointer to the individual TIM registers.
JW
2021-04-26 10:36 PM
Oh,Thanks very much. you are right! This program run ok!