You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mynewt.apache.org by ma...@apache.org on 2016/04/11 23:25:45 UTC
[15/28] incubator-mynewt-core git commit: Get rid of 'os_arch_idle()'
in favor of calling 'os_tick_idle()' directly from the idle task. This was
motivated by the fact that on most platforms the OS tick will be generated by
a MCU-specific timer which impl
Get rid of 'os_arch_idle()' in favor of calling 'os_tick_idle()' directly
from the idle task. This was motivated by the fact that on most platforms
the OS tick will be generated by a MCU-specific timer which implies that
the idle function will also be MCU-specific.
Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/f59995ec
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/f59995ec
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/f59995ec
Branch: refs/heads/develop
Commit: f59995ecd33ed99997cffd6e04884fc69bf875c4
Parents: 1dcc28c
Author: Neel Natu <ne...@nahannisys.com>
Authored: Wed Apr 6 11:57:17 2016 -0700
Committer: Neel Natu <ne...@nahannisys.com>
Committed: Wed Apr 6 11:57:17 2016 -0700
----------------------------------------------------------------------
hw/bsp/nrf52pdk/src/os_bsp.c | 141 -----------------
hw/hal/include/hal/hal_os_tick.h | 35 +++++
hw/mcu/nordic/nrf51xxx/src/hal_os_tick.c | 29 ++++
hw/mcu/nordic/nrf52xxx/src/hal_os_tick.c | 158 ++++++++++++++++++++
libs/os/include/os/arch/cortex_m0/os/os_arch.h | 1 -
libs/os/include/os/arch/cortex_m4/os/os_arch.h | 1 -
libs/os/include/os/arch/sim/os/os_arch.h | 1 -
libs/os/src/arch/cortex_m0/os_arch_arm.c | 13 --
libs/os/src/arch/cortex_m4/os_arch_arm.c | 10 +-
libs/os/src/arch/sim/os_arch_sim.c | 2 +-
libs/os/src/os.c | 4 +-
11 files changed, 228 insertions(+), 167 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/hw/bsp/nrf52pdk/src/os_bsp.c
----------------------------------------------------------------------
diff --git a/hw/bsp/nrf52pdk/src/os_bsp.c b/hw/bsp/nrf52pdk/src/os_bsp.c
index f386137..d1e8809 100644
--- a/hw/bsp/nrf52pdk/src/os_bsp.c
+++ b/hw/bsp/nrf52pdk/src/os_bsp.c
@@ -16,12 +16,6 @@
* specific language governing permissions and limitations
* under the License.
*/
-#include <assert.h>
-
-#include <os/os.h>
-#include <bsp/cmsis_nvic.h>
-#include <mcu/nrf52.h>
-#include <mcu/nrf52_bitfields.h>
#include <util/util.h>
#include <hal/flash_map.h>
@@ -83,138 +77,3 @@ os_bsp_init(void)
flash_area_init(bsp_flash_areas,
sizeof(bsp_flash_areas) / sizeof(bsp_flash_areas[0]));
}
-
-#define CALLOUT_TIMER NRF_TIMER1
-#define CALLOUT_IRQ TIMER1_IRQn
-#define CALLOUT_CMPREG 0 /* generate timer interrupt */
-#define CALLOUT_COUNTER 1 /* capture current timer value */
-#define CALLOUT_PRESCALER 4 /* prescaler to generate 1MHz timer freq */
-#define TIMER_LT(__t1, __t2) ((int32_t)((__t1) - (__t2)) < 0)
-
-static int timer_ticks_per_ostick;
-static os_time_t nrf52_max_idle_ticks;
-static uint32_t lastocmp;
-
-static inline uint32_t
-nrf52_callout_counter(void)
-{
- /*
- * Make sure we are not interrupted between invoking the capture task
- * and reading the value.
- */
- OS_ASSERT_CRITICAL();
-
- /*
- * Capture the current timer value and return it.
- */
- CALLOUT_TIMER->TASKS_CAPTURE[CALLOUT_COUNTER] = 1;
- return (CALLOUT_TIMER->CC[CALLOUT_COUNTER]);
-}
-
-static inline void
-nrf52_callout_set_ocmp(uint32_t ocmp)
-{
- uint32_t counter;
-
- OS_ASSERT_CRITICAL();
- while (1) {
- CALLOUT_TIMER->CC[CALLOUT_CMPREG] = ocmp;
- counter = nrf52_callout_counter();
- if (TIMER_LT(counter, ocmp)) {
- break;
- }
- ocmp += timer_ticks_per_ostick;
- }
-}
-
-static void
-nrf52_timer_handler(void)
-{
- int ticks;
- os_sr_t sr;
- uint32_t counter;
-
- OS_ENTER_CRITICAL(sr);
-
- /*
- * Calculate elapsed ticks and advance OS time.
- */
- counter = nrf52_callout_counter();
- ticks = (counter - lastocmp) / timer_ticks_per_ostick;
- os_time_advance(ticks);
-
- /* Clear timer interrupt */
- CALLOUT_TIMER->EVENTS_COMPARE[CALLOUT_CMPREG] = 0;
-
- /* Update the time associated with the most recent tick */
- lastocmp += ticks * timer_ticks_per_ostick;
-
- /* Update the output compare to interrupt at the next tick */
- nrf52_callout_set_ocmp(lastocmp + timer_ticks_per_ostick);
-
- OS_EXIT_CRITICAL(sr);
-}
-
-void
-os_bsp_idle(os_time_t ticks)
-{
- uint32_t ocmp;
-
- OS_ASSERT_CRITICAL();
-
- if (ticks > 0) {
- /*
- * Enter tickless regime during long idle durations.
- */
- if (ticks > nrf52_max_idle_ticks) {
- ticks = nrf52_max_idle_ticks;
- }
- ocmp = lastocmp + ticks * timer_ticks_per_ostick;
- nrf52_callout_set_ocmp(ocmp);
- }
-
- __DSB();
- __WFI();
-
- if (ticks > 0) {
- /*
- * Update OS time before anything else when coming out of
- * the tickless regime.
- */
- nrf52_timer_handler();
- }
-}
-
-void
-os_bsp_systick_init(uint32_t os_ticks_per_sec, int prio)
-{
- lastocmp = 0;
- timer_ticks_per_ostick = 1000000 / os_ticks_per_sec;
-
- /*
- * The maximum number of timer ticks allowed to elapse during idle is
- * limited to 1/4th the number of timer ticks before the counter rolls
- * over.
- */
- nrf52_max_idle_ticks = (1UL << 30) / timer_ticks_per_ostick;
-
- /*
- * Program CALLOUT_TIMER to operate at 1MHz and trigger an output
- * compare interrupt at a rate of 'os_ticks_per_sec'.
- */
- CALLOUT_TIMER->TASKS_STOP = 1;
- CALLOUT_TIMER->TASKS_CLEAR = 1;
- CALLOUT_TIMER->MODE = TIMER_MODE_MODE_Timer;
- CALLOUT_TIMER->BITMODE = TIMER_BITMODE_BITMODE_32Bit;
- CALLOUT_TIMER->PRESCALER = CALLOUT_PRESCALER;
-
- CALLOUT_TIMER->CC[CALLOUT_CMPREG] = timer_ticks_per_ostick;
- CALLOUT_TIMER->INTENSET = TIMER_COMPARE_INT_MASK(CALLOUT_CMPREG);
- CALLOUT_TIMER->EVENTS_COMPARE[CALLOUT_CMPREG] = 0;
-
- NVIC_SetPriority(CALLOUT_IRQ, prio);
- NVIC_SetVector(CALLOUT_IRQ, (uint32_t)nrf52_timer_handler);
- NVIC_EnableIRQ(CALLOUT_IRQ);
-
- CALLOUT_TIMER->TASKS_START = 1; /* start the callout timer */
-}
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/hw/hal/include/hal/hal_os_tick.h
----------------------------------------------------------------------
diff --git a/hw/hal/include/hal/hal_os_tick.h b/hw/hal/include/hal/hal_os_tick.h
new file mode 100644
index 0000000..dce419e
--- /dev/null
+++ b/hw/hal/include/hal/hal_os_tick.h
@@ -0,0 +1,35 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+#ifndef _HAL_OS_TICK_H_
+#define _HAL_OS_TICK_H_
+
+#include <os/os_time.h>
+
+/*
+ * Set up the periodic timer to interrupt at a frequency of 'os_ticks_per_sec'.
+ * 'prio' is the cpu-specific priority of the periodic timer interrupt.
+ */
+void os_tick_init(uint32_t os_ticks_per_sec, int prio);
+
+/*
+ * Halt CPU for up to 'n' ticks.
+ */
+void os_tick_idle(os_time_t n);
+
+#endif
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/hw/mcu/nordic/nrf51xxx/src/hal_os_tick.c
----------------------------------------------------------------------
diff --git a/hw/mcu/nordic/nrf51xxx/src/hal_os_tick.c b/hw/mcu/nordic/nrf51xxx/src/hal_os_tick.c
new file mode 100644
index 0000000..665abd9
--- /dev/null
+++ b/hw/mcu/nordic/nrf51xxx/src/hal_os_tick.c
@@ -0,0 +1,29 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+#include <assert.h>
+#include <os/os.h>
+#include <hal/hal_os_tick.h>
+
+void
+os_tick_idle(os_time_t ticks)
+{
+ OS_ASSERT_CRITICAL();
+ __DSB();
+ __WFI();
+}
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/hw/mcu/nordic/nrf52xxx/src/hal_os_tick.c
----------------------------------------------------------------------
diff --git a/hw/mcu/nordic/nrf52xxx/src/hal_os_tick.c b/hw/mcu/nordic/nrf52xxx/src/hal_os_tick.c
new file mode 100644
index 0000000..abded0e
--- /dev/null
+++ b/hw/mcu/nordic/nrf52xxx/src/hal_os_tick.c
@@ -0,0 +1,158 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+#include <assert.h>
+#include <os/os.h>
+#include <hal/hal_os_tick.h>
+#include <mcu/nrf52_bitfields.h>
+#include <bsp/cmsis_nvic.h>
+
+#define CALLOUT_TIMER NRF_TIMER1
+#define CALLOUT_IRQ TIMER1_IRQn
+#define CALLOUT_CMPREG 0 /* generate timer interrupt */
+#define CALLOUT_COUNTER 1 /* capture current timer value */
+#define CALLOUT_PRESCALER 4 /* prescaler to generate 1MHz timer freq */
+#define TIMER_LT(__t1, __t2) ((int32_t)((__t1) - (__t2)) < 0)
+
+static int timer_ticks_per_ostick;
+static os_time_t nrf52_max_idle_ticks;
+static uint32_t lastocmp;
+
+static inline uint32_t
+nrf52_callout_counter(void)
+{
+ /*
+ * Make sure we are not interrupted between invoking the capture task
+ * and reading the value.
+ */
+ OS_ASSERT_CRITICAL();
+
+ /*
+ * Capture the current timer value and return it.
+ */
+ CALLOUT_TIMER->TASKS_CAPTURE[CALLOUT_COUNTER] = 1;
+ return (CALLOUT_TIMER->CC[CALLOUT_COUNTER]);
+}
+
+static inline void
+nrf52_callout_set_ocmp(uint32_t ocmp)
+{
+ uint32_t counter;
+
+ OS_ASSERT_CRITICAL();
+ while (1) {
+ CALLOUT_TIMER->CC[CALLOUT_CMPREG] = ocmp;
+ counter = nrf52_callout_counter();
+ if (TIMER_LT(counter, ocmp)) {
+ break;
+ }
+ ocmp += timer_ticks_per_ostick;
+ }
+}
+
+static void
+nrf52_timer_handler(void)
+{
+ int ticks;
+ os_sr_t sr;
+ uint32_t counter;
+
+ OS_ENTER_CRITICAL(sr);
+
+ /*
+ * Calculate elapsed ticks and advance OS time.
+ */
+ counter = nrf52_callout_counter();
+ ticks = (counter - lastocmp) / timer_ticks_per_ostick;
+ os_time_advance(ticks);
+
+ /* Clear timer interrupt */
+ CALLOUT_TIMER->EVENTS_COMPARE[CALLOUT_CMPREG] = 0;
+
+ /* Update the time associated with the most recent tick */
+ lastocmp += ticks * timer_ticks_per_ostick;
+
+ /* Update the output compare to interrupt at the next tick */
+ nrf52_callout_set_ocmp(lastocmp + timer_ticks_per_ostick);
+
+ OS_EXIT_CRITICAL(sr);
+}
+
+void
+os_tick_idle(os_time_t ticks)
+{
+ uint32_t ocmp;
+
+ OS_ASSERT_CRITICAL();
+
+ if (ticks > 0) {
+ /*
+ * Enter tickless regime during long idle durations.
+ */
+ if (ticks > nrf52_max_idle_ticks) {
+ ticks = nrf52_max_idle_ticks;
+ }
+ ocmp = lastocmp + ticks * timer_ticks_per_ostick;
+ nrf52_callout_set_ocmp(ocmp);
+ }
+
+ __DSB();
+ __WFI();
+
+ if (ticks > 0) {
+ /*
+ * Update OS time before anything else when coming out of
+ * the tickless regime.
+ */
+ nrf52_timer_handler();
+ }
+}
+
+void
+os_tick_init(uint32_t os_ticks_per_sec, int prio)
+{
+ lastocmp = 0;
+ timer_ticks_per_ostick = 1000000 / os_ticks_per_sec;
+
+ /*
+ * The maximum number of timer ticks allowed to elapse during idle is
+ * limited to 1/4th the number of timer ticks before the counter rolls
+ * over.
+ */
+ nrf52_max_idle_ticks = (1UL << 30) / timer_ticks_per_ostick;
+
+ /*
+ * Program CALLOUT_TIMER to operate at 1MHz and trigger an output
+ * compare interrupt at a rate of 'os_ticks_per_sec'.
+ */
+ CALLOUT_TIMER->TASKS_STOP = 1;
+ CALLOUT_TIMER->TASKS_CLEAR = 1;
+ CALLOUT_TIMER->MODE = TIMER_MODE_MODE_Timer;
+ CALLOUT_TIMER->BITMODE = TIMER_BITMODE_BITMODE_32Bit;
+ CALLOUT_TIMER->PRESCALER = CALLOUT_PRESCALER;
+
+ CALLOUT_TIMER->CC[CALLOUT_CMPREG] = timer_ticks_per_ostick;
+ CALLOUT_TIMER->INTENSET = TIMER_COMPARE_INT_MASK(CALLOUT_CMPREG);
+ CALLOUT_TIMER->EVENTS_COMPARE[CALLOUT_CMPREG] = 0;
+
+ NVIC_SetPriority(CALLOUT_IRQ, prio);
+ NVIC_SetVector(CALLOUT_IRQ, (uint32_t)nrf52_timer_handler);
+ NVIC_EnableIRQ(CALLOUT_IRQ);
+
+ CALLOUT_TIMER->TASKS_START = 1; /* start the callout timer */
+}
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/libs/os/include/os/arch/cortex_m0/os/os_arch.h
----------------------------------------------------------------------
diff --git a/libs/os/include/os/arch/cortex_m0/os/os_arch.h b/libs/os/include/os/arch/cortex_m0/os/os_arch.h
index 23016c7..7231cb7 100755
--- a/libs/os/include/os/arch/cortex_m0/os/os_arch.h
+++ b/libs/os/include/os/arch/cortex_m0/os/os_arch.h
@@ -66,7 +66,6 @@ os_error_t os_arch_os_start(void);
void os_set_env(void);
void os_arch_init_task_stack(os_stack_t *sf);
void os_default_irq_asm(void);
-void os_arch_idle(os_time_t ticks);
/* External function prototypes supplied by BSP */
void os_bsp_systick_init(uint32_t os_ticks_per_sec, int prio);
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/libs/os/include/os/arch/cortex_m4/os/os_arch.h
----------------------------------------------------------------------
diff --git a/libs/os/include/os/arch/cortex_m4/os/os_arch.h b/libs/os/include/os/arch/cortex_m4/os/os_arch.h
index a68f38a..590542a 100755
--- a/libs/os/include/os/arch/cortex_m4/os/os_arch.h
+++ b/libs/os/include/os/arch/cortex_m4/os/os_arch.h
@@ -66,7 +66,6 @@ os_error_t os_arch_os_start(void);
void os_set_env(void);
void os_arch_init_task_stack(os_stack_t *sf);
void os_default_irq_asm(void);
-void os_arch_idle(os_time_t ticks);
/* External function prototypes supplied by BSP */
void os_bsp_systick_init(uint32_t os_tick_per_sec, int prio);
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/libs/os/include/os/arch/sim/os/os_arch.h
----------------------------------------------------------------------
diff --git a/libs/os/include/os/arch/sim/os/os_arch.h b/libs/os/include/os/arch/sim/os/os_arch.h
index b1368ee..6b98b8e 100644
--- a/libs/os/include/os/arch/sim/os/os_arch.h
+++ b/libs/os/include/os/arch/sim/os/os_arch.h
@@ -70,7 +70,6 @@ int os_arch_in_critical(void);
os_error_t os_arch_os_init(void);
void os_arch_os_stop(void);
os_error_t os_arch_os_start(void);
-void os_arch_idle(os_time_t ticks);
void os_bsp_init(void);
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/libs/os/src/arch/cortex_m0/os_arch_arm.c
----------------------------------------------------------------------
diff --git a/libs/os/src/arch/cortex_m0/os_arch_arm.c b/libs/os/src/arch/cortex_m0/os_arch_arm.c
index e8cf44f..8a2015c 100755
--- a/libs/os/src/arch/cortex_m0/os_arch_arm.c
+++ b/libs/os/src/arch/cortex_m0/os_arch_arm.c
@@ -329,16 +329,3 @@ os_arch_os_start(void)
return err;
}
-
-void
-os_arch_idle(os_time_t ticks)
-{
- os_sr_t sr;
-
- OS_ENTER_CRITICAL(sr);
- __DSB();
- __WFI();
- OS_EXIT_CRITICAL(sr);
-
- return;
-}
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/libs/os/src/arch/cortex_m4/os_arch_arm.c
----------------------------------------------------------------------
diff --git a/libs/os/src/arch/cortex_m4/os_arch_arm.c b/libs/os/src/arch/cortex_m4/os_arch_arm.c
index dc91e84..b9c0c1d 100755
--- a/libs/os/src/arch/cortex_m4/os_arch_arm.c
+++ b/libs/os/src/arch/cortex_m4/os_arch_arm.c
@@ -19,7 +19,7 @@
#include "os/os.h"
#include "os/os_arch.h"
-
+#include <hal/hal_os_tick.h>
#include <bsp/cmsis_nvic.h>
/* Initial program status register */
@@ -246,7 +246,7 @@ os_arch_start(void)
__set_PSP((uint32_t)t->t_stackptr + offsetof(struct stack_frame, r0));
/* Intitialize and start system clock timer */
- os_bsp_systick_init(OS_TICKS_PER_SEC, SYSTICK_PRIO);
+ os_tick_init(OS_TICKS_PER_SEC, SYSTICK_PRIO);
/* Mark the OS as started, right before we run our first task */
g_os_started = 1;
@@ -322,9 +322,3 @@ os_arch_os_start(void)
return err;
}
-
-void
-os_arch_idle(os_time_t ticks)
-{
- os_bsp_idle(ticks);
-}
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/libs/os/src/arch/sim/os_arch_sim.c
----------------------------------------------------------------------
diff --git a/libs/os/src/arch/sim/os_arch_sim.c b/libs/os/src/arch/sim/os_arch_sim.c
index bbdc641..521d51a 100644
--- a/libs/os/src/arch/sim/os_arch_sim.c
+++ b/libs/os/src/arch/sim/os_arch_sim.c
@@ -177,7 +177,7 @@ os_arch_in_critical(void)
}
void
-os_arch_idle(os_time_t ticks)
+os_tick_idle(os_time_t ticks)
{
int rc;
struct itimerval it;
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/f59995ec/libs/os/src/os.c
----------------------------------------------------------------------
diff --git a/libs/os/src/os.c b/libs/os/src/os.c
index 4310178..963fc40 100644
--- a/libs/os/src/os.c
+++ b/libs/os/src/os.c
@@ -20,6 +20,8 @@
#include "os/os.h"
#include "os/queue.h"
+#include "hal/hal_os_tick.h"
+
#include <assert.h>
struct os_task g_idle_task;
@@ -59,7 +61,7 @@ os_idle_task(void *arg)
} else {
/* NOTHING */
}
- os_arch_idle(iticks);
+ os_tick_idle(iticks);
OS_EXIT_CRITICAL(sr);
}
}