mbed library sources

Dependents:   frdm_kl05z_gpio_test

Fork of mbed-src by mbed official

Committer:
shaoziyang
Date:
Sat Sep 13 14:25:46 2014 +0000
Revision:
323:9e901b0a5aa1
Parent:
304:89b9c3a9a045
test with CLOCK_SETUP = 0

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mbed_official 181:a4cbdfbbd2f4 1 /* mbed Microcontroller Library
mbed_official 181:a4cbdfbbd2f4 2 * Copyright (c) 2014, STMicroelectronics
mbed_official 181:a4cbdfbbd2f4 3 * All rights reserved.
mbed_official 181:a4cbdfbbd2f4 4 *
mbed_official 181:a4cbdfbbd2f4 5 * Redistribution and use in source and binary forms, with or without
mbed_official 181:a4cbdfbbd2f4 6 * modification, are permitted provided that the following conditions are met:
mbed_official 181:a4cbdfbbd2f4 7 *
mbed_official 181:a4cbdfbbd2f4 8 * 1. Redistributions of source code must retain the above copyright notice,
mbed_official 181:a4cbdfbbd2f4 9 * this list of conditions and the following disclaimer.
mbed_official 181:a4cbdfbbd2f4 10 * 2. Redistributions in binary form must reproduce the above copyright notice,
mbed_official 181:a4cbdfbbd2f4 11 * this list of conditions and the following disclaimer in the documentation
mbed_official 181:a4cbdfbbd2f4 12 * and/or other materials provided with the distribution.
mbed_official 181:a4cbdfbbd2f4 13 * 3. Neither the name of STMicroelectronics nor the names of its contributors
mbed_official 181:a4cbdfbbd2f4 14 * may be used to endorse or promote products derived from this software
mbed_official 181:a4cbdfbbd2f4 15 * without specific prior written permission.
mbed_official 181:a4cbdfbbd2f4 16 *
mbed_official 181:a4cbdfbbd2f4 17 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
mbed_official 181:a4cbdfbbd2f4 18 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
mbed_official 181:a4cbdfbbd2f4 19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
mbed_official 181:a4cbdfbbd2f4 20 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
mbed_official 181:a4cbdfbbd2f4 21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
mbed_official 181:a4cbdfbbd2f4 22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
mbed_official 181:a4cbdfbbd2f4 23 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
mbed_official 181:a4cbdfbbd2f4 24 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
mbed_official 181:a4cbdfbbd2f4 25 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
mbed_official 181:a4cbdfbbd2f4 26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
mbed_official 181:a4cbdfbbd2f4 27 */
mbed_official 181:a4cbdfbbd2f4 28 #include <stddef.h>
mbed_official 181:a4cbdfbbd2f4 29 #include "us_ticker_api.h"
mbed_official 181:a4cbdfbbd2f4 30 #include "PeripheralNames.h"
mbed_official 181:a4cbdfbbd2f4 31
mbed_official 181:a4cbdfbbd2f4 32 // Timer selection:
mbed_official 181:a4cbdfbbd2f4 33 #define TIM_MST TIM21
mbed_official 181:a4cbdfbbd2f4 34 #define TIM_MST_IRQ TIM21_IRQn
mbed_official 181:a4cbdfbbd2f4 35 #define TIM_MST_RCC __TIM21_CLK_ENABLE()
mbed_official 181:a4cbdfbbd2f4 36
mbed_official 181:a4cbdfbbd2f4 37 static TIM_HandleTypeDef TimMasterHandle;
mbed_official 181:a4cbdfbbd2f4 38
mbed_official 181:a4cbdfbbd2f4 39 static int us_ticker_inited = 0;
mbed_official 181:a4cbdfbbd2f4 40 static volatile uint32_t SlaveCounter = 0;
mbed_official 181:a4cbdfbbd2f4 41 static volatile uint32_t oc_int_part = 0;
mbed_official 181:a4cbdfbbd2f4 42 static volatile uint16_t oc_rem_part = 0;
mbed_official 181:a4cbdfbbd2f4 43
mbed_official 181:a4cbdfbbd2f4 44 void set_compare(uint16_t count) {
mbed_official 181:a4cbdfbbd2f4 45 // Set new output compare value
mbed_official 181:a4cbdfbbd2f4 46 __HAL_TIM_SetCompare(&TimMasterHandle, TIM_CHANNEL_1, count);
mbed_official 181:a4cbdfbbd2f4 47 // Enable IT
mbed_official 181:a4cbdfbbd2f4 48 __HAL_TIM_ENABLE_IT(&TimMasterHandle, TIM_IT_CC1);
mbed_official 181:a4cbdfbbd2f4 49 }
mbed_official 181:a4cbdfbbd2f4 50
mbed_official 181:a4cbdfbbd2f4 51 static void tim_irq_handler(void) {
mbed_official 181:a4cbdfbbd2f4 52 uint16_t cval = TIM_MST->CNT;
mbed_official 181:a4cbdfbbd2f4 53
mbed_official 248:0df67d8046d9 54 // Clear Update interrupt flag
mbed_official 248:0df67d8046d9 55 if (__HAL_TIM_GET_FLAG(&TimMasterHandle, TIM_FLAG_UPDATE) == SET) {
mbed_official 248:0df67d8046d9 56 __HAL_TIM_CLEAR_FLAG(&TimMasterHandle, TIM_FLAG_UPDATE);
mbed_official 181:a4cbdfbbd2f4 57 SlaveCounter++;
mbed_official 181:a4cbdfbbd2f4 58 }
mbed_official 181:a4cbdfbbd2f4 59
mbed_official 248:0df67d8046d9 60 // Clear CC1 interrupt flag
mbed_official 248:0df67d8046d9 61 if (__HAL_TIM_GET_FLAG(&TimMasterHandle, TIM_FLAG_CC1) == SET) {
mbed_official 248:0df67d8046d9 62 __HAL_TIM_CLEAR_FLAG(&TimMasterHandle, TIM_FLAG_CC1);
mbed_official 181:a4cbdfbbd2f4 63 if (oc_rem_part > 0) {
mbed_official 181:a4cbdfbbd2f4 64 set_compare(oc_rem_part); // Finish the remaining time left
mbed_official 181:a4cbdfbbd2f4 65 oc_rem_part = 0;
mbed_official 181:a4cbdfbbd2f4 66 } else {
mbed_official 181:a4cbdfbbd2f4 67 if (oc_int_part > 0) {
mbed_official 181:a4cbdfbbd2f4 68 set_compare(0xFFFF);
mbed_official 181:a4cbdfbbd2f4 69 oc_rem_part = cval; // To finish the counter loop the next time
mbed_official 181:a4cbdfbbd2f4 70 oc_int_part--;
mbed_official 181:a4cbdfbbd2f4 71 } else {
mbed_official 181:a4cbdfbbd2f4 72 us_ticker_irq_handler();
mbed_official 181:a4cbdfbbd2f4 73 }
mbed_official 181:a4cbdfbbd2f4 74 }
mbed_official 181:a4cbdfbbd2f4 75 }
mbed_official 181:a4cbdfbbd2f4 76 }
mbed_official 181:a4cbdfbbd2f4 77
mbed_official 181:a4cbdfbbd2f4 78 void us_ticker_init(void) {
mbed_official 181:a4cbdfbbd2f4 79 if (us_ticker_inited) return;
mbed_official 181:a4cbdfbbd2f4 80 us_ticker_inited = 1;
mbed_official 181:a4cbdfbbd2f4 81
mbed_official 181:a4cbdfbbd2f4 82 // Enable timer clock
mbed_official 181:a4cbdfbbd2f4 83 TIM_MST_RCC;
mbed_official 181:a4cbdfbbd2f4 84
mbed_official 181:a4cbdfbbd2f4 85 // Configure time base
mbed_official 181:a4cbdfbbd2f4 86 TimMasterHandle.Instance = TIM_MST;
mbed_official 181:a4cbdfbbd2f4 87 TimMasterHandle.Init.Period = 0xFFFF;
mbed_official 304:89b9c3a9a045 88 TimMasterHandle.Init.Prescaler = (uint32_t)(SystemCoreClock / 1000000) - 1; // 1 �s tick
mbed_official 181:a4cbdfbbd2f4 89 TimMasterHandle.Init.ClockDivision = 0;
mbed_official 181:a4cbdfbbd2f4 90 TimMasterHandle.Init.CounterMode = TIM_COUNTERMODE_UP;
mbed_official 181:a4cbdfbbd2f4 91 HAL_TIM_Base_Init(&TimMasterHandle);
mbed_official 181:a4cbdfbbd2f4 92
mbed_official 181:a4cbdfbbd2f4 93 // Configure interrupts
mbed_official 181:a4cbdfbbd2f4 94 __HAL_TIM_ENABLE_IT(&TimMasterHandle, TIM_IT_UPDATE);
mbed_official 181:a4cbdfbbd2f4 95
mbed_official 181:a4cbdfbbd2f4 96 // Update interrupt used for 32-bit counter
mbed_official 181:a4cbdfbbd2f4 97 // Output compare interrupt used for timeout feature
mbed_official 181:a4cbdfbbd2f4 98 NVIC_SetVector(TIM_MST_IRQ, (uint32_t)tim_irq_handler);
mbed_official 181:a4cbdfbbd2f4 99 NVIC_EnableIRQ(TIM_MST_IRQ);
mbed_official 181:a4cbdfbbd2f4 100
mbed_official 181:a4cbdfbbd2f4 101 // Enable timer
mbed_official 181:a4cbdfbbd2f4 102 HAL_TIM_Base_Start(&TimMasterHandle);
mbed_official 181:a4cbdfbbd2f4 103 }
mbed_official 181:a4cbdfbbd2f4 104
mbed_official 181:a4cbdfbbd2f4 105 uint32_t us_ticker_read() {
mbed_official 181:a4cbdfbbd2f4 106 uint32_t counter, counter2;
mbed_official 181:a4cbdfbbd2f4 107 if (!us_ticker_inited) us_ticker_init();
mbed_official 181:a4cbdfbbd2f4 108 // A situation might appear when Master overflows right after Slave is read and before the
mbed_official 181:a4cbdfbbd2f4 109 // new (overflowed) value of Master is read. Which would make the code below consider the
mbed_official 181:a4cbdfbbd2f4 110 // previous (incorrect) value of Slave and the new value of Master, which would return a
mbed_official 181:a4cbdfbbd2f4 111 // value in the past. Avoid this by computing consecutive values of the timer until they
mbed_official 181:a4cbdfbbd2f4 112 // are properly ordered.
mbed_official 181:a4cbdfbbd2f4 113 counter = (uint32_t)(SlaveCounter << 16);
mbed_official 181:a4cbdfbbd2f4 114 counter += TIM_MST->CNT;
mbed_official 181:a4cbdfbbd2f4 115 while (1) {
mbed_official 181:a4cbdfbbd2f4 116 counter2 = (uint32_t)(SlaveCounter << 16);
mbed_official 181:a4cbdfbbd2f4 117 counter2 += TIM_MST->CNT;
mbed_official 181:a4cbdfbbd2f4 118 if (counter2 > counter) {
mbed_official 181:a4cbdfbbd2f4 119 break;
mbed_official 181:a4cbdfbbd2f4 120 }
mbed_official 181:a4cbdfbbd2f4 121 counter = counter2;
mbed_official 181:a4cbdfbbd2f4 122 }
mbed_official 181:a4cbdfbbd2f4 123 return counter2;
mbed_official 181:a4cbdfbbd2f4 124 }
mbed_official 181:a4cbdfbbd2f4 125
mbed_official 304:89b9c3a9a045 126 void us_ticker_set_interrupt(timestamp_t timestamp) {
mbed_official 304:89b9c3a9a045 127 int delta = (int)((uint32_t)timestamp - us_ticker_read());
mbed_official 181:a4cbdfbbd2f4 128 uint16_t cval = TIM_MST->CNT;
mbed_official 181:a4cbdfbbd2f4 129
mbed_official 181:a4cbdfbbd2f4 130 if (delta <= 0) { // This event was in the past
mbed_official 181:a4cbdfbbd2f4 131 us_ticker_irq_handler();
mbed_official 181:a4cbdfbbd2f4 132 } else {
mbed_official 181:a4cbdfbbd2f4 133 oc_int_part = (uint32_t)(delta >> 16);
mbed_official 181:a4cbdfbbd2f4 134 oc_rem_part = (uint16_t)(delta & 0xFFFF);
mbed_official 181:a4cbdfbbd2f4 135 if (oc_rem_part <= (0xFFFF - cval)) {
mbed_official 181:a4cbdfbbd2f4 136 set_compare(cval + oc_rem_part);
mbed_official 181:a4cbdfbbd2f4 137 oc_rem_part = 0;
mbed_official 181:a4cbdfbbd2f4 138 } else {
mbed_official 181:a4cbdfbbd2f4 139 set_compare(0xFFFF);
mbed_official 181:a4cbdfbbd2f4 140 oc_rem_part = oc_rem_part - (0xFFFF - cval);
mbed_official 181:a4cbdfbbd2f4 141 }
mbed_official 181:a4cbdfbbd2f4 142 }
mbed_official 181:a4cbdfbbd2f4 143 }
mbed_official 181:a4cbdfbbd2f4 144
mbed_official 181:a4cbdfbbd2f4 145 void us_ticker_disable_interrupt(void) {
mbed_official 181:a4cbdfbbd2f4 146 __HAL_TIM_DISABLE_IT(&TimMasterHandle, TIM_IT_CC1);
mbed_official 181:a4cbdfbbd2f4 147 }
mbed_official 181:a4cbdfbbd2f4 148
mbed_official 181:a4cbdfbbd2f4 149 void us_ticker_clear_interrupt(void) {
mbed_official 248:0df67d8046d9 150 __HAL_TIM_CLEAR_FLAG(&TimMasterHandle, TIM_FLAG_CC1);
mbed_official 181:a4cbdfbbd2f4 151 }