Skip to main content
filippo2991
Associate III
April 27, 2010
Question

fastest way to generate output waveform

  • April 27, 2010
  • 4 replies
  • 848 views
Posted on April 27, 2010 at 12:10

fastest way to generate output waveform

    This topic has been closed for replies.

    4 replies

    Andrew Neil
    Super User
    May 17, 2011
    Posted on May 17, 2011 at 13:48

    ''''I''ll put some code for fast PWM''

    But he didn't want PWM;  just a fixed-period, fixed duty cycle - and not very fast at that!

    A complex system that works is invariably found to have evolved from a simple system that worked.A complex system designed from scratch never works and cannot be patched up to make it work.
    smart2
    Visitor II
    May 17, 2011
    Posted on May 17, 2011 at 13:48

     Do some efforts its not that hard just take help from STM32 library code

    If still not get sucess ''ll put some code fot fast PWM with period 50 usec(yes usec not msec...) and with variable duty cycle output.

    Andrew Neil
    Super User
    May 17, 2011
    Posted on May 17, 2011 at 13:48

    PWM, in this context, is 

    P

    ulse

    W

    idth

    M

    odulation

    http://en.wikipedia.org/wiki/Pulse-width_modulation

    A complex system that works is invariably found to have evolved from a simple system that worked.A complex system designed from scratch never works and cannot be patched up to make it work.
    filippo2991
    Associate III
    May 17, 2011
    Posted on May 17, 2011 at 13:48

    I got it working using TIMx as Toggle, here is my init and interrupt routine. I choosed a prescaler value and parametrized CC1 register to have different freq/duty cycle. In the service routine I select the counter toggle value in order to have the right duty cycle. Is that the better way to do this?

    Would you explain to me what is the PWM? I'm just learning and I really get lost. Thanks and best regards.

    Filippo

    void Waveform_On(void)

    {

      NVIC_InitTypeDef NVIC_InitStructure;

      GPIO_InitTypeDef GPIO_InitStructure;

     

      /* TIM3 clock enable */

      RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);

      /* GPIOA clock enable */

      RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_GPIOB|

                             RCC_APB2Periph_GPIOC | RCC_APB2Periph_AFIO, ENABLE);

     

        /* Enable the TIM3 global Interrupt */

      NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;

      NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;

      NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;

      NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;

      NVIC_Init(&NVIC_InitStructure);

      

        // timer out

      GPIO_InitStructure.GPIO_Pin =  GPIO_Pin_6;

      GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;

      GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;

      GPIO_Init(GPIOC, &GPIO_InitStructure);

      GPIO_PinRemapConfig(GPIO_FullRemap_TIM3, ENABLE); 

     

    // timer init

      /* Time base configuration */

      TIM_TimeBaseStructure.TIM_Period = 65535;

      TIM_TimeBaseStructure.TIM_Prescaler = TIM3_PRESCALER;

      TIM_TimeBaseStructure.TIM_ClockDivision = 0;

      TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;

      TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);

      /* Output Compare Toggle Mode configuration: Channel1 */

      TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_Toggle;

      TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;

      TIM_OCInitStructure.TIM_Pulse = TIM3_CCR1_ON;

      TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_Low;

      TIM_OC1Init(TIM3, &TIM_OCInitStructure);

      TIM_OC1PreloadConfig(TIM3, TIM_OCPreload_Disable);

      /* TIM enable counter */

      TIM_Cmd(TIM3, ENABLE);

      /* TIM IT enable */

      TIM_ITConfig(TIM3, TIM_IT_CC1, ENABLE); 

     }

    #define TV0ON 5 // ms

    #define TV0_DUTYCYCLE 10 // in %

    #if defined(CORE_CLOCK_36MHZ)

      #define TIM3_PRESCALER 72

      #define TIM3_CCR1_ON (36000000 / 2000 / TIM3_PRESCALER * TV0ON)

      #define TIM3_CCR1_OFF (TIM3_CCR1_ON * ((100-TV0_DUTYCYCLE)/TV0_DUTYCYCLE))

    #elif defined(CORE_CLOCK_8MHZ)

      #define TIM3_PRESCALER 16

      #define TIM3_CCR1_ON  (8000000 / 2000 / TIM3_PRESCALER * TV0ON)

      #define TIM3_CCR1_OFF (TIM3_CCR1_ON * ((100-TV0_DUTYCYCLE)/TV0_DUTYCYCLE))

    #endif

    void TIM3_IRQHandler(void)

    {

      if (TIM_GetITStatus(TIM3, TIM_IT_CC1) != RESET)

      {

        TIM_ClearITPendingBit(TIM3, TIM_IT_CC1 );

        capture = TIM_GetCapture1(TIM3);

        if (V0STATUS)

        {

          V0STATUS = 0;

          TIM_SetCompare1(TIM3, capture + TIM3_CCR1_ON );

        }

        else

        {

          V0STATUS = 1;

          TIM_SetCompare1(TIM3, capture + TIM3_CCR1_OFF );

        }

       

      }

    }