mbed library sources

Dependents:   frdm_kl05z_gpio_test

Fork of mbed-src by mbed official

Revision:
304:89b9c3a9a045
Parent:
300:55638feb26a4
diff -r 78e31413b129 -r 89b9c3a9a045 targets/hal/TARGET_NORDIC/TARGET_MCU_NRF51822/us_ticker.c
--- a/targets/hal/TARGET_NORDIC/TARGET_MCU_NRF51822/us_ticker.c	Fri Aug 29 11:45:07 2014 +0100
+++ b/targets/hal/TARGET_NORDIC/TARGET_MCU_NRF51822/us_ticker.c	Fri Aug 29 17:15:07 2014 +0100
@@ -17,113 +17,88 @@
 #include "us_ticker_api.h"
 #include "cmsis.h"
 #include "PeripheralNames.h"
-
-#define US_TICKER_TIMER      NRF_TIMER1
-#define US_TICKER_TIMER_IRQn TIMER1_IRQn
-
-int us_ticker_inited        = 0;
-volatile uint16_t overflow  = 0; //overflow value that forms the upper 16 bits of the counter
-volatile uint16_t timeStamp = 0;
-
-#ifdef __cplusplus
-extern "C" {
-#endif
+#include "app_timer.h"
 
-void TIMER1_IRQHandler(void)
-{
-    if ((US_TICKER_TIMER->EVENTS_COMPARE[1] != 0) &&
-        ((US_TICKER_TIMER->INTENSET & TIMER_INTENSET_COMPARE1_Msk) != 0)) {
-        US_TICKER_TIMER->EVENTS_COMPARE[1] = 0;
-        overflow++;
-        US_TICKER_TIMER->CC[1] = 0xFFFF;
-        if (timeStamp>0) {
-            timeStamp--;
-            if (timeStamp==0) {
-                us_ticker_clear_interrupt();
-                us_ticker_disable_interrupt();
-                us_ticker_irq_handler();
-                return;
-            }
-        }
-    }
-    if ((US_TICKER_TIMER->EVENTS_COMPARE[0] != 0) &&
-        ((US_TICKER_TIMER->INTENSET & TIMER_INTENSET_COMPARE0_Msk) != 0)) {
-        us_ticker_clear_interrupt();
-        us_ticker_disable_interrupt();
-        if (timeStamp==0) {
-            us_ticker_irq_handler();
-        }
-    }
-}
+static bool           us_ticker_inited          = false;
+static volatile bool  us_ticker_appTimerRunning = false;
+static app_timer_id_t us_ticker_appTimerID      = TIMER_NULL;
 
-#ifdef __cplusplus
-}
-#endif
 void us_ticker_init(void)
 {
-    if (us_ticker_inited && US_TICKER_TIMER->POWER) {
+    if (us_ticker_inited) {
         return;
     }
 
-    us_ticker_inited = 1;
-
-    US_TICKER_TIMER->POWER = 0;
-    US_TICKER_TIMER->POWER = 1;
-
-    US_TICKER_TIMER->MODE = TIMER_MODE_MODE_Timer;
+    APP_TIMER_INIT(0 /*CFG_TIMER_PRESCALER*/ , 1 /*CFG_TIMER_MAX_INSTANCE*/, 1 /*CFG_TIMER_OPERATION_QUEUE_SIZE*/, false /*CFG_SCHEDULER_ENABLE*/);
 
-    US_TICKER_TIMER->PRESCALER   = 4;
-    US_TICKER_TIMER->BITMODE     = TIMER_BITMODE_BITMODE_16Bit;
-    US_TICKER_TIMER->TASKS_CLEAR = 1;
-    US_TICKER_TIMER->CC[1]       = 0xFFFF;
-    US_TICKER_TIMER->INTENSET    = TIMER_INTENSET_COMPARE1_Set << TIMER_INTENSET_COMPARE1_Pos;
-
-    NVIC_SetPriority(US_TICKER_TIMER_IRQn, 3);
-    NVIC_EnableIRQ(US_TICKER_TIMER_IRQn);
-
-    US_TICKER_TIMER->TASKS_START = 0x01;
+    us_ticker_inited = true;
 }
 
 uint32_t us_ticker_read()
 {
-    if (!us_ticker_inited || (US_TICKER_TIMER->POWER==0)) {
+    if (!us_ticker_inited) {
+        us_ticker_init();
+    }
+
+    timestamp_t value;
+    app_timer_cnt_get(&value); /* This returns the RTC counter (which is fed by the 32khz crystal clock source) */
+    return (uint32_t)((value * 1000000) / APP_TIMER_CLOCK_FREQ); /* Return a pseudo microsecond counter value.
+                                                                  * This is only as precise as the 32khz low-freq
+                                                                  * clock source, but could be adequate.*/
+}
+
+/* An adaptor to interface us_ticker_irq_handler with the app_timer callback.
+ * Needed because the irq_handler() doesn't take any parameter.*/
+static void us_ticker_app_timer_callback(void *context)
+{
+    us_ticker_appTimerRunning = false;
+    us_ticker_irq_handler();
+}
+
+void us_ticker_set_interrupt(timestamp_t timestamp)
+{
+    if (!us_ticker_inited) {
         us_ticker_init();
     }
 
-    uint16_t bufferedOverFlow =         overflow;
-    US_TICKER_TIMER->TASKS_CAPTURE[2] = 1;
-
-    if (overflow!=bufferedOverFlow) {
-        bufferedOverFlow                  = overflow;
-        US_TICKER_TIMER->TASKS_CAPTURE[2] = 1;
+    if (us_ticker_appTimerID == TIMER_NULL) {
+        if (app_timer_create(&us_ticker_appTimerID, APP_TIMER_MODE_SINGLE_SHOT, us_ticker_app_timer_callback) != NRF_SUCCESS) {
+            /* placeholder to do something to recover from error */
+            return;
+        }
     }
-    return (((uint32_t)bufferedOverFlow << 16) | US_TICKER_TIMER->CC[2]);
-}
 
-void us_ticker_set_interrupt(unsigned int timestamp)
-{
-    if (!us_ticker_inited || (US_TICKER_TIMER->POWER == 0)) {
-        us_ticker_init();
+    if (us_ticker_appTimerRunning) {
+        return;
     }
 
-    US_TICKER_TIMER->TASKS_CAPTURE[0] = 1;
-    uint16_t tsUpper16 = (uint16_t)((timestamp - us_ticker_read()) >> 16);
-    if (tsUpper16>0) {
-        if ((timeStamp ==0) || (timeStamp> tsUpper16)) {
-            timeStamp = tsUpper16;
+    timestamp_t currentCounter64;
+    app_timer_cnt_get(&currentCounter64);
+    uint32_t currentCounter = currentCounter64 & MAX_RTC_COUNTER_VAL;
+    uint32_t targetCounter = ((uint32_t)((timestamp * (uint64_t)APP_TIMER_CLOCK_FREQ) / 1000000) + 1) & MAX_RTC_COUNTER_VAL;
+    uint32_t ticksToCount = (targetCounter >= currentCounter) ?
+                             (targetCounter - currentCounter) : (MAX_RTC_COUNTER_VAL + 1) - (currentCounter - targetCounter);
+    if (ticksToCount > 0) {
+        uint32_t rc;
+        rc = app_timer_start(us_ticker_appTimerID, ticksToCount, NULL /*p_context*/);
+        if (rc != NRF_SUCCESS) {
+            /* placeholder to do something to recover from error */
+            return;
         }
-    } else {
-        US_TICKER_TIMER->INTENSET |= TIMER_INTENSET_COMPARE0_Set << TIMER_INTENSET_COMPARE0_Pos;
-        US_TICKER_TIMER->CC[0]    += timestamp - us_ticker_read();
+        us_ticker_appTimerRunning = true;
     }
 }
 
 void us_ticker_disable_interrupt(void)
 {
-    US_TICKER_TIMER->INTENCLR = TIMER_INTENCLR_COMPARE0_Clear << TIMER_INTENCLR_COMPARE0_Pos;
+    if (us_ticker_appTimerRunning) {
+        app_timer_stop(us_ticker_appTimerID);
+    }
 }
 
 void us_ticker_clear_interrupt(void)
 {
-    US_TICKER_TIMER->EVENTS_COMPARE[0] = 0;
+    if (us_ticker_appTimerRunning) {
+        app_timer_stop(us_ticker_appTimerID);
+    }
 }