Skip to content

Commit be920e7

Browse files
committed
Move CuriePowerMangement library as part of cores
-move the Power Management library from https://github.com/bigdinotech/Arduino101Power
1 parent c794c47 commit be920e7

15 files changed

+5048
-0
lines changed
+296
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,296 @@
1+
Table of Contents
2+
=================
3+
4+
* [CuriePower](#curiepower)
5+
* [CuriePower API reference](#curiepower-api-reference)
6+
* [Functions](#functions)
7+
* [CuriePower.doze()](#curiepowerdoze)
8+
* [CuriePower.doze(int duration)](#curiepowerdozeint-duration)
9+
* [CuriePower.idle()](#curiepoweridle)
10+
* [CuriePower.idle(int duration)](#curiepoweridleint-duration)
11+
* [CuriePower.sleep()](#curiepowersleep)
12+
* [CuriePower.sleep(int duration)](#curiepowersleepint-duration)
13+
* [CuriePower.deepSleep()](#curiepowerdeepsleep)
14+
* [CuriePower.deepSleep(int duration)](#curiepowerdeepsleepint-duration)
15+
* [CuriePower.attachInterruptWakeup(uint32_t pin, voidFuncPtr callback, uint32_t mode)](#curiepowerattachinterruptwakeupuint32_t-pin-voidfuncptr-callback-uint32_t-mode)
16+
* [CuriePower.detachInterruptWakeup(uint32_t pin)](#curiepowerdetachinterruptwakeupuint32_t-pin)
17+
* [Tutorials](#tutorials)
18+
* [Tutorial #1: TimedWakeup Example](#tutorial-1-timedwakeup-example)
19+
* [Tutorial #2: WakeFromIMU Example](#tutorial-2-wakefromimu-example)
20+
21+
# CuriePower
22+
CuriePower is a Power Management library for Curie based boards such as the Arduino101/Genuino101 and tinyTILE
23+
24+
# CuriePower API reference
25+
26+
## Functions
27+
28+
### ``CuriePower.doze()``
29+
30+
```
31+
void CuriePower.doze()
32+
```
33+
34+
Places the SoC in "doze" mode which switches the system clock to the internal 32.768 kHz RTC oscillator.
35+
36+
*Parameters*
37+
38+
none
39+
40+
*Return value*
41+
42+
none
43+
44+
### ``CuriePower.doze(int duration)``
45+
46+
```
47+
void CuriePower.doze(int duration)
48+
```
49+
50+
51+
Places the SoC in "doze" mode which switches the system clock to the internal 32.768 kHz RTC oscillator for `duration` milliseconds
52+
53+
54+
*Parameters*
55+
56+
1. `int duration` : number in milliseconds to doze
57+
58+
*Return value*
59+
60+
none
61+
62+
### ``CuriePower.idle()``
63+
64+
```
65+
void CuriePower.idle()
66+
```
67+
68+
Places the SoC into "doze" mode then enters an infinite loop, effectively stopping all operations until a wake interrupt is generated.
69+
70+
*Parameters*
71+
72+
none
73+
74+
*Return value*
75+
76+
none
77+
78+
### ``CuriePower.idle(int duration)``
79+
80+
```
81+
void CuriePower.idle(int duration)
82+
```
83+
84+
85+
Places the SoC in "doze" mode and enters an infinite loop for `duration` milliseconds
86+
87+
88+
*Parameters*
89+
90+
1. `int duration` : number in milliseconds to idle
91+
92+
*Return value*
93+
94+
none
95+
96+
### ``CuriePower.sleep()``
97+
98+
```
99+
void CuriePower.sleep()
100+
```
101+
102+
Places the SoC into a sleep state, stopping all operations, until a wake interrupt is generated
103+
104+
*Parameters*
105+
106+
none
107+
108+
*Return value*
109+
110+
none
111+
112+
### ``CuriePower.sleep(int duration)``
113+
114+
```
115+
void CuriePower.sleep(int duration)
116+
```
117+
118+
119+
Places the SoC into a sleep state for `duration` milliseconds
120+
121+
122+
*Parameters*
123+
124+
1. `int duration` : number in milliseconds to sleep
125+
126+
*Return value*
127+
128+
none
129+
130+
### ``CuriePower.deepSleep()``
131+
132+
```
133+
void CuriePower.deepSleep()
134+
```
135+
136+
Places the SoC into a deep sleep state, stopping all operations, until a wake interrupt is generated
137+
138+
*Parameters*
139+
140+
none
141+
142+
*Return value*
143+
144+
none
145+
146+
### ``CuriePower.deepSleep(int duration)``
147+
148+
```
149+
void CuriePower.deepSleep(int duration)
150+
```
151+
152+
153+
Places the SoC into a deep sleep state for `duration` milliseconds
154+
155+
156+
*Parameters*
157+
158+
1. `int duration` : number in milliseconds to deep sleep
159+
160+
*Return value*
161+
162+
none
163+
164+
### ``CuriePower.attachInterruptWakeup(uint32_t pin, voidFuncPtr callback, uint32_t mode)``
165+
166+
```
167+
void CuriePower.attachInterruptWakeup(uint32_t pin, voidFuncPtr callback, uint32_t mode)
168+
```
169+
170+
Attaches a wakeup interrupt to digital pin `pin`. `callback` is the function to be called when the wakeup interrupt occurs.
171+
172+
*Parameters*
173+
174+
none
175+
176+
*Return value*
177+
178+
none
179+
180+
### ``CuriePower.detachInterruptWakeup(uint32_t pin)``
181+
182+
```
183+
void CuriePower.detachInterruptWakeup(uint32_t pin)
184+
```
185+
186+
Removes any wakeup interrupt attached to digital pin `pin`.
187+
188+
*Parameters*
189+
190+
none
191+
192+
*Return value*
193+
194+
none
195+
196+
# Tutorials
197+
198+
## Tutorial #1: TimedWakeup Example
199+
200+
This sketch demonstrates the simplest way to use the CuriePower library. It blinks the LED a few times, goes to sleep for a certain amount of time then goes back at the start of loop()
201+
202+
```cpp
203+
#include <Power.h>
204+
205+
void setup() {
206+
pinMode(LED_BUILTIN, OUTPUT);
207+
}
208+
209+
void loop() {
210+
for(int i = 0; i < 5; i++)
211+
{
212+
digitalWrite(LED_BUILTIN, HIGH);
213+
delay(100);
214+
digitalWrite(LED_BUILTIN, LOW);
215+
delay(100);
216+
}
217+
PM.sleep(1000);
218+
}
219+
```
220+
221+
The line of code that is most interesting here is:
222+
```cpp
223+
PM.sleep(1000);
224+
```
225+
This puts the SoC into sleep, drawing significantly less power, for 1000ms or 1s.
226+
227+
In what situations is this most useful?
228+
229+
Let's says you have a battery powered project that reads a sensor value once every second and saves it to an SD card.
230+
Simply using delay() will work but you will notice that you will run out of battery pretty fast. That is because even though the code is not doing much inside delay, it is still running everything at full clock speed and all peripherals are turned on.
231+
When we put the SoC to sleep, several things are turned off. This includes most of the peripherals. voltage rails, and some clocks. Basically, it draws much less power and no code is running until a wake interrupt is generated.
232+
233+
Many Arduino projects typically have a loop where you read a sensor, do something with that reading, and then delay for a set amount of time.
234+
In most cases, reading the sensor and doing something with that reading takes very little time, much smaller than the delay duration. This means that we are wasting a lot of power inside the delay doing nothing.
235+
By placing the SoC to sleep instead of just waiting inside the delay, we can save a considerable amount of power in most applications.
236+
237+
238+
## Tutorial #2: WakeFromIMU Example
239+
240+
This sketch uses CuriePower library and the CurieIMU library together and demonstrates the use of an interrupt to wake the Curie SoC from sleep.
241+
242+
```cpp
243+
#include <Power.h>
244+
#include "CurieIMU.h"
245+
246+
247+
void setup() {
248+
pinMode(LED_BUILTIN, OUTPUT);
249+
CurieIMU.begin();
250+
CurieIMU.attachInterrupt(wakeup);
251+
CurieIMU.setDetectionThreshold(CURIE_IMU_MOTION, 20); // 100mg
252+
CurieIMU.setDetectionDuration(CURIE_IMU_MOTION, 10); // trigger times of consecutive slope data points
253+
CurieIMU.interrupts(CURIE_IMU_MOTION);
254+
255+
}
256+
257+
void loop() {
258+
PM.sleep();
259+
digitalWrite(LED_BUILTIN, HIGH);
260+
delay(3000);
261+
digitalWrite(LED_BUILTIN, LOW);
262+
}
263+
264+
void wakeup()
265+
{
266+
PM.wakeFromDoze();
267+
// This function will be called once on device wakeup
268+
// You can do some little operations here (like changing variables which will be used in the loop)
269+
// Remember to avoid calling delay() and long running functions since this functions executes in interrupt context
270+
}
271+
```
272+
273+
If you look at the beginning of loop() you will see:
274+
```cpp
275+
PM.sleep();
276+
```
277+
This line of code puts the SoC into a sleep state. The SoC will remain in a sleep state until it is woken by an interrupt.
278+
If no interrupt triggers the SoC to wake up, it will stay in a sleep state forever(or until the battery runs out).
279+
This is specifically useful in applications that are not periodic, like in this example sketch where the SoC stays at a sleep state until the Arduino101 detects motion, or more precisely the Bosch BMI160 [6-Axis Accelerometer/Gyroscope] sensor detects the motion and triggers an interrupt to wake the Curie Soc from sleep.
280+
281+
Inside setup() we have:
282+
```cpp
283+
CurieIMU.attachInterrupt(wakeup);
284+
CurieIMU.setDetectionThreshold(CURIE_IMU_MOTION, 20); // 100mg
285+
CurieIMU.setDetectionDuration(CURIE_IMU_MOTION, 10); // trigger times of consecutive slope data points
286+
CurieIMU.interrupts(CURIE_IMU_MOTION);
287+
```
288+
These lines of code attaches a method called wakeup() which is called whenever motion is detected. Since the interrupt signal generated by the Bosch BMI160 sensor is already internally connected to AON(Always On) interrupt of the SoC, it automatically wakes the SoC from sleep.
289+
However, since we are using the attachInterrupt() method of the CurieIMU Library instead of the one from the CuriePower Library we still need to do one more thing after the SoC is taken out of a sleep state.
290+
291+
Inside the wakeup() method:
292+
```cpp
293+
PM.wakeFromDoze();
294+
```
295+
This line of code simply takes the SoC out of the Doze state, switching it from using the internal RTC 32.768 KHz as the main clock, back to the 32Mhz oscillator.
296+
At this point the SoC runs back at full speed ready to do stuff quickly and then go back to sleep to save power.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
#include <Power.h>
2+
3+
void setup() {
4+
pinMode(LED_BUILTIN, OUTPUT);
5+
}
6+
7+
void loop() {
8+
for(int i = 0; i < 5; i++)
9+
{
10+
digitalWrite(LED_BUILTIN, HIGH);
11+
delay(100);
12+
digitalWrite(LED_BUILTIN, LOW);
13+
delay(100);
14+
}
15+
PM.sleep(1000);
16+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
#include <Power.h>
2+
#include "CurieIMU.h"
3+
4+
5+
void setup() {
6+
pinMode(LED_BUILTIN, OUTPUT);
7+
CurieIMU.begin();
8+
CurieIMU.attachInterrupt(wakeup);
9+
CurieIMU.setDetectionThreshold(CURIE_IMU_MOTION, 20); // 100mg
10+
CurieIMU.setDetectionDuration(CURIE_IMU_MOTION, 10); // trigger times of consecutive slope data points
11+
CurieIMU.interrupts(CURIE_IMU_MOTION);
12+
13+
}
14+
15+
void loop() {
16+
PM.sleep();
17+
digitalWrite(LED_BUILTIN, HIGH);
18+
delay(3000);
19+
digitalWrite(LED_BUILTIN, LOW);
20+
}
21+
22+
void wakeup()
23+
{
24+
PM.wakeFromDoze();
25+
// This function will be called once on device wakeup
26+
// You can do some little operations here (like changing variables which will be used in the loop)
27+
// Remember to avoid calling delay() and long running functions since this functions executes in interrupt context
28+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
#######################################
2+
# Syntax Coloring Map For Curie Power Library
3+
#######################################
4+
5+
#######################################
6+
# Datatypes (KEYWORD1)
7+
#######################################
8+
9+
#######################################
10+
# Methods and Functions (KEYWORD2)
11+
#######################################
12+
sleep KEYWORD2
13+
deepSleep KEYWORD2
14+
idle KEYWORD2
15+
doze KEYWORD2
16+
wakeFromDoze KEYWORD2
17+
18+
#######################################
19+
# Instances (KEYWORD2)
20+
#######################################
21+
22+
#######################################
23+
# Constants (LITERAL1)
24+
#######################################
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
name=CuriePowerManagement
2+
version=1.0
3+
author=Intel
4+
maintainer=Intel <[email protected]>
5+
sentence=Curie Power Management library for Curie based boards.
6+
paragraph=Allows to manage the power states of Curie based boards.
7+
category=Device Control
8+
url=
9+
architectures=arc32

0 commit comments

Comments
 (0)