AnsweredAssumed Answered

STM32F0: Getting PWM Output to Work

Question asked by FarrellF on Oct 8, 2012
Latest reply on Oct 11, 2012 by FarrellF
I can get PWM output to work with my F4 MCUs, but I can't get it to work with the F0. My code is below, any ideas? As you can see, I'm not using the STM libraries, I am only using their stm32f0xx.h header for register definitions.

#include "stm32f0xx.h"

#include "core_cm0.h"

void TIM1_BRK_UP_TRG_COM_IRQHandler();                      // ISR prototype


int main() {

    RCC->AHBENR |= RCC_AHBENR_GPIOAEN;                      // Enable GPIOA clock
    GPIOA->MODER |= GPIO_MODER_MODER8_1;                    // Pin A8 mode = Alt Function
    GPIOA->AFR[1] |= 0b0010;                                // Pin A8 alt function = AF2 (TIM1)
    GPIOA->OSPEEDR |= GPIO_OSPEEDER_OSPEEDR8;               // Pin A8 speed = 50MHz

    RCC->APB2ENR |= RCC_APB2ENR_TIM1EN;                     // Enable clock
    TIM1->PSC = 23;                                         // Prescaler = 23 (1 tick per half microsecond)
    TIM1->ARR = 19999;                                      // Auto-reload = PWM frequency in half microseconds = 10ms period
    TIM1->CCMR1 |= TIM_CCMR1_OC1M_1 | TIM_CCMR1_OC1M_2;     // OC1M = 110 for PWM Mode 1 output on ch1
    TIM1->CCMR1 |= TIM_CCMR1_OC1PE;                         // Output 1 preload enable
    TIM1->CR1 |= TIM_CR1_ARPE;                              // Auto-reload preload enable
    TIM1->CCER |= TIM_CCER_CC1E;                            // Enable output for ch1
    TIM1->CCR1 = 1800;                                      // CCR1 = Duty cycle in half microseconds = high for 900us
    TIM1->EGR |= TIM_EGR_UG;                                // Force update
    TIM1->SR &= ~TIM_SR_UIF;                                // Clear the update flag
    TIM1->DIER |= TIM_DIER_UIE;                             // Enable interrupt on update event
    NVIC_EnableIRQ(TIM1_BRK_UP_TRG_COM_IRQn);               // Enable IRQ
    TIM1->CR1 |= TIM_CR1_CEN;                               // Enable counter

    while(1) {
    }
}

void TIM1_BRK_UP_TRG_COM_IRQHandler() {

    if(TIM1->SR & TIM_SR_UIF != 0) {                        // If update flag is set
        // do stuff here if needed
    }
    TIM1->SR &= ~TIM_SR_UIF;                                // Interrupt has been handled
}

Outcomes