/examples/stm32/f1/stm32-h103/timer/timer.c
https://github.com/kkmonster/libopencm3-examples · C · 167 lines · 87 code · 33 blank · 47 comment · 4 complexity · cae5fe4797b83bff2637ecffd74b5c0f MD5 · raw file
- /*
- * This file is part of the libopencm3 project.
- *
- * Copyright (C) 2011 Piotr Esden-Tempski <piotr@esden.net>
- *
- * This library is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this library. If not, see <http://www.gnu.org/licenses/>.
- */
- #include <libopencm3/stm32/rcc.h>
- #include <libopencm3/stm32/gpio.h>
- #include <libopencm3/stm32/timer.h>
- #include <libopencm3/cm3/nvic.h>
- #include <libopencm3/stm32/exti.h>
- uint16_t frequency_sequence[18] = {
- 1000,
- 500,
- 1000,
- 500,
- 1000,
- 500,
- 2000,
- 500,
- 2000,
- 500,
- 2000,
- 500,
- 1000,
- 500,
- 1000,
- 500,
- 1000,
- 5000,
- };
- int frequency_sel = 0;
- uint16_t compare_time;
- uint16_t new_time;
- uint16_t frequency;
- int debug = 0;
- static void clock_setup(void)
- {
- rcc_clock_setup_in_hse_8mhz_out_72mhz();
- }
- static void gpio_setup(void)
- {
- /* Enable GPIOC clock. */
- rcc_periph_clock_enable(RCC_GPIOC);
- /* Set GPIO12 (in GPIO port C) to 'output push-pull'. */
- gpio_set_mode(GPIOC, GPIO_MODE_OUTPUT_50_MHZ,
- GPIO_CNF_OUTPUT_PUSHPULL, GPIO12);
- gpio_set(GPIOC, GPIO12);
- }
- static void tim_setup(void)
- {
- /* Enable TIM2 clock. */
- rcc_periph_clock_enable(RCC_TIM2);
- /* Enable TIM2 interrupt. */
- nvic_enable_irq(NVIC_TIM2_IRQ);
- /* Reset TIM2 peripheral. */
- timer_reset(TIM2);
- /* Timer global mode:
- * - No divider
- * - Alignment edge
- * - Direction up
- */
- timer_set_mode(TIM2, TIM_CR1_CKD_CK_INT,
- TIM_CR1_CMS_EDGE, TIM_CR1_DIR_UP);
- /* Reset prescaler value. */
- timer_set_prescaler(TIM2, 36000);
- /* Enable preload. */
- timer_disable_preload(TIM2);
- /* Continous mode. */
- timer_continuous_mode(TIM2);
- /* Period (36kHz). */
- timer_set_period(TIM2, 65535);
- /* Disable outputs. */
- timer_disable_oc_output(TIM2, TIM_OC1);
- timer_disable_oc_output(TIM2, TIM_OC2);
- timer_disable_oc_output(TIM2, TIM_OC3);
- timer_disable_oc_output(TIM2, TIM_OC4);
- /* -- OC1 configuration -- */
- /* Configure global mode of line 1. */
- timer_disable_oc_clear(TIM2, TIM_OC1);
- timer_disable_oc_preload(TIM2, TIM_OC1);
- timer_set_oc_slow_mode(TIM2, TIM_OC1);
- timer_set_oc_mode(TIM2, TIM_OC1, TIM_OCM_FROZEN);
- /* Set the capture compare value for OC1. */
- timer_set_oc_value(TIM2, TIM_OC1, 1000);
- /* ---- */
- /* ARR reload enable. */
- timer_disable_preload(TIM2);
- /* Counter enable. */
- timer_enable_counter(TIM2);
- /* Enable commutation interrupt. */
- timer_enable_irq(TIM2, TIM_DIER_CC1IE);
- }
- void tim2_isr(void)
- {
- if (timer_get_flag(TIM2, TIM_SR_CC1IF)) {
- /* Clear compare interrupt flag. */
- timer_clear_flag(TIM2, TIM_SR_CC1IF);
- /*
- * Get current timer value to calculate next
- * compare register value.
- */
- compare_time = timer_get_counter(TIM2);
- /* Calculate and set the next compare value. */
- frequency = frequency_sequence[frequency_sel++];
- new_time = compare_time + frequency;
- timer_set_oc_value(TIM2, TIM_OC1, new_time);
- if (frequency_sel == 18)
- frequency_sel = 0;
- /* Toggle LED to indicate compare event. */
- gpio_toggle(GPIOC, GPIO12);
- }
- }
- int main(void)
- {
- clock_setup();
- gpio_setup();
- tim_setup();
- while (1)
- __asm("nop");
- return 0;
- }