1
\$\begingroup\$

Hello i woul'd like change PWM period with DMA. I wrote code but i don't know why LED BLINKING with constant time

#include "stm32f10x.h"
#include "stm32f1xx_nucleo.h"
#include "stm32f10x.h"

int i =0;
u16 PWM_Buf[198];

void TIMInit(void);
void GPIOInit(void);
void DMAInit(void);
void PWMInit(void);

int main(void)
{
 GPIOInit();
 TIMInit();
 DMAInit();
 PWMInit();

 for(i = 0;i<198;i++)
 {
  PWM_Buf[i] = i * 10; // <-------- VALUE OF TIM PERIOD
 }


    while(1)
    {
    }
}
void TIMInit(void)
{
 TIM_TimeBaseInitTypeDef TIMInit;

 RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1, ENABLE);

    TIMInit.TIM_Period = 1000;
    TIMInit.TIM_Prescaler = 64000;

    TIMInit.TIM_ClockDivision = TIM_CKD_DIV1;
    TIMInit.TIM_CounterMode = TIM_CounterMode_Up;

    TIMInit.TIM_RepetitionCounter = 200;

    TIM_TimeBaseInit(TIM1, &TIMInit);
}

void GPIOInit(void)
{
  GPIO_InitTypeDef GPIOInit;

 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
 RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);

   GPIOInit.GPIO_Pin = GPIO_Pin_8;
   GPIOInit.GPIO_Mode = GPIO_Mode_AF_PP;
   GPIOInit.GPIO_Speed = GPIO_Speed_50MHz;

   GPIO_Init(GPIOA, &GPIOInit);
}

void DMAInit(void)
{
 #define TIM1_ARR_Address 0X40012C2C

 DMA_InitTypeDef DMAInit;

 RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);
 DMA_DeInit(DMA1_Channel5);
 DMAInit.DMA_PeripheralBaseAddr = (u16)TIM1_ARR_Address;
 DMAInit.DMA_MemoryBaseAddr = (u32)PWM_Buf;
 DMAInit.DMA_DIR = DMA_DIR_PeripheralDST;
 DMAInit.DMA_BufferSize = 198;
 DMAInit.DMA_PeripheralInc = DMA_PeripheralInc_Enable;
 DMAInit.DMA_MemoryInc = DMA_MemoryInc_Enable;
 DMAInit.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Word;
 DMAInit.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;
 DMAInit.DMA_Mode = DMA_Mode_Circular;
 DMAInit.DMA_Priority = DMA_Priority_High;
 DMAInit.DMA_M2M = DMA_M2M_Disable;

 DMA_Init(DMA1_Channel5, &DMAInit);

    DMA_Cmd(DMA1_Channel5, ENABLE);
}

void PWMInit(void)
{
 TIM_OCInitTypeDef  PWMInit;

    PWMInit.TIM_OCMode = TIM_OCMode_PWM1;
    PWMInit.TIM_OutputState = TIM_OutputState_Enable;
    PWMInit.TIM_Pulse = 500;
    PWMInit.TIM_OCPolarity = TIM_OCPolarity_High;
    TIM_OC1Init(TIM1, &PWMInit);
    TIM_OC1PreloadConfig(TIM1, TIM_OCPreload_Enable);
    TIM_ARRPreloadConfig(TIM1, ENABLE);
    TIM_DMACmd(TIM1, TIM_DMA_Update, ENABLE);
    TIM_Cmd(TIM1, ENABLE);
    TIM_CtrlPWMOutputs(TIM1, ENABLE);
}
\$\endgroup\$
  • \$\begingroup\$ Thank you for providing the full source code along with the question. \$\endgroup\$ – Morten Jensen Jan 29 '18 at 14:37
  • \$\begingroup\$ It's not full code i cutted usart communication, and motor driver. I only paste DMA TIMER AND PWM configuration. I thought i wrote good code but i dont know why period doesnt be diffrent. I need only help for it. \$\endgroup\$ – Member Cicada Jan 29 '18 at 14:42
  • \$\begingroup\$ Are you sure this is correct? DMAInit.DMA_PeripheralInc = DMA_PeripheralInc_Enable; Does this really want to be set to inc? I suspect this is at least one issue you have and it wants to be DMA_PeripheralInc_Disable. I think. \$\endgroup\$ – DiBosco Jan 29 '18 at 14:54
  • \$\begingroup\$ It's not probably problem i disabled this and the same. I don't see anything wrong. I thought someone maybe caught problem \$\endgroup\$ – Member Cicada Jan 29 '18 at 15:02
  • \$\begingroup\$ You need to put @DiBosco for me to see your response. When I did this to create PWMs many years back, my DMA's CPAR register was set to the CCR, not the ARR register which I think you have used here. \$\endgroup\$ – DiBosco Jan 29 '18 at 15:46
1
\$\begingroup\$
DMAInit.DMA_PeripheralBaseAddr = (u16)TIM1_ARR_Address;  

You can't cast a pointer as an unsigned 16 bit. Pointers are 32 bit on this platform.
Like this: (uint32_t)&TIM1->ARR.

DMAInit.DMA_PeripheralInc = DMA_PeripheralInc_Enable;

You can't increment the peripheral address, the next cycle would be TIMx_RCR, then TIMx_CCR1 etc.

\$\endgroup\$
  • \$\begingroup\$ I'd already pointed out the peripheral inc thing to him and he'd said that'd made no difference. The pointer thing is good point though. \$\endgroup\$ – DiBosco Jan 29 '18 at 15:47
  • \$\begingroup\$ I know it's stupid, but can I ask for the code to be corrected because I have no idea how to do it. I would be very grateful \$\endgroup\$ – Member Cicada Jan 29 '18 at 17:00
  • \$\begingroup\$ I wonder how you wrote this code if you have no idea what to change or at least articulate yourself to ask what to change!!? \$\endgroup\$ – charansai Jan 29 '18 at 20:09
  • \$\begingroup\$ @MemberCicada why have you configured PeripheralDataSize as word and MemoryDataSize as half word? \$\endgroup\$ – charansai Jan 29 '18 at 20:24
  • 1
    \$\begingroup\$ @charansai the timer is 16 bit and half word access is possible. \$\endgroup\$ – Jeroen3 Jan 30 '18 at 7:05

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.