Improve sleep and add button waking
This commit is contained in:
+32
-4
@@ -66,6 +66,11 @@ static void imuInt1ISR() {
|
|||||||
imuWakeFlag = true;
|
imuWakeFlag = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static volatile bool btnWakeFlag = false;
|
||||||
|
static void btnWakeISR() {
|
||||||
|
btnWakeFlag = true;
|
||||||
|
}
|
||||||
|
|
||||||
// Arm wakeup interrupt
|
// Arm wakeup interrupt
|
||||||
static void armWakeupInterrupt() {
|
static void armWakeupInterrupt() {
|
||||||
lsmWrite(SLP_WAKE_UP_DUR, (uint8_t)((SLEEP_WAKEUP_DUR & 0x03) << 4));
|
lsmWrite(SLP_WAKE_UP_DUR, (uint8_t)((SLEEP_WAKEUP_DUR & 0x03) << 4));
|
||||||
@@ -127,6 +132,15 @@ static void enterImuLP() {
|
|||||||
|
|
||||||
armWakeupInterrupt();
|
armWakeupInterrupt();
|
||||||
|
|
||||||
|
// Arm button wake interrupt
|
||||||
|
#if BTN_LEFT_PIN != BTN_PIN_NONE
|
||||||
|
btnWakeFlag = false;
|
||||||
|
attachInterrupt(digitalPinToInterrupt(BTN_LEFT_PIN), btnWakeISR, FALLING);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Turn off all LEDs for sleep
|
||||||
|
digitalWrite(LED_RED, HIGH); digitalWrite(LED_GREEN, HIGH); digitalWrite(LED_BLUE, HIGH);
|
||||||
|
|
||||||
lpEnteredMs = millis();
|
lpEnteredMs = millis();
|
||||||
sleepStage = SLEEP_IMU_LP;
|
sleepStage = SLEEP_IMU_LP;
|
||||||
Serial.print("[SLEEP] IMU LP entered - idle for ");
|
Serial.print("[SLEEP] IMU LP entered - idle for ");
|
||||||
@@ -153,9 +167,9 @@ static void enterDeepSleep() {
|
|||||||
Serial.println("[SLEEP] Deep sleep - WFE on INT1");
|
Serial.println("[SLEEP] Deep sleep - WFE on INT1");
|
||||||
Serial.flush();
|
Serial.flush();
|
||||||
|
|
||||||
digitalWrite(LED_RED, LOW); delay(80); digitalWrite(LED_RED, HIGH);
|
digitalWrite(LED_RED, HIGH); digitalWrite(LED_GREEN, HIGH); digitalWrite(LED_BLUE, HIGH);
|
||||||
|
|
||||||
while (!imuWakeFlag) {
|
while (!imuWakeFlag && !btnWakeFlag) {
|
||||||
(void)lsmRead(SLP_WAKE_UP_SRC);
|
(void)lsmRead(SLP_WAKE_UP_SRC);
|
||||||
sd_app_evt_wait();
|
sd_app_evt_wait();
|
||||||
}
|
}
|
||||||
@@ -172,6 +186,11 @@ void sleepManagerWakeIMU() {
|
|||||||
|
|
||||||
disarmWakeupInterrupt();
|
disarmWakeupInterrupt();
|
||||||
|
|
||||||
|
// Detach button wake interrupt — normal polling takes over
|
||||||
|
#if BTN_LEFT_PIN != BTN_PIN_NONE
|
||||||
|
detachInterrupt(digitalPinToInterrupt(BTN_LEFT_PIN));
|
||||||
|
#endif
|
||||||
|
|
||||||
// Only recalibrate if gyro was off long enough for thermal drift to accumulate,
|
// Only recalibrate if gyro was off long enough for thermal drift to accumulate,
|
||||||
// or if waking from full deep sleep. Short LP naps reuse the existing bias.
|
// or if waking from full deep sleep. Short LP naps reuse the existing bias.
|
||||||
unsigned long lpDuration = millis() - lpEnteredMs;
|
unsigned long lpDuration = millis() - lpEnteredMs;
|
||||||
@@ -225,14 +244,23 @@ void sleepManagerInit() {
|
|||||||
// Returns true → caller must skip IMU reads this iteration.
|
// Returns true → caller must skip IMU reads this iteration.
|
||||||
bool sleepManagerUpdate(unsigned long nowMs, bool idle, bool bleConnected) {
|
bool sleepManagerUpdate(unsigned long nowMs, bool idle, bool bleConnected) {
|
||||||
|
|
||||||
// ISR wakeup
|
// ISR wakeup (IMU motion or button press)
|
||||||
|
bool woke = false;
|
||||||
if (imuWakeFlag) {
|
if (imuWakeFlag) {
|
||||||
imuWakeFlag = false;
|
imuWakeFlag = false;
|
||||||
Serial.print("[SLEEP] INT1 fired - stage="); Serial.println((int)sleepStage);
|
Serial.print("[SLEEP] INT1 fired - stage="); Serial.println((int)sleepStage);
|
||||||
|
woke = true;
|
||||||
|
}
|
||||||
|
if (btnWakeFlag) {
|
||||||
|
btnWakeFlag = false;
|
||||||
|
Serial.print("[SLEEP] Button fired - stage="); Serial.println((int)sleepStage);
|
||||||
|
woke = true;
|
||||||
|
}
|
||||||
|
if (woke) {
|
||||||
if (sleepStage == SLEEP_DEEP || sleepStage == SLEEP_IMU_LP) {
|
if (sleepStage == SLEEP_DEEP || sleepStage == SLEEP_IMU_LP) {
|
||||||
sleepManagerWakeIMU();
|
sleepManagerWakeIMU();
|
||||||
} else {
|
} else {
|
||||||
(void)lsmRead(SLP_WAKE_UP_SRC); // normal-mode edge, clear latch only
|
(void)lsmRead(SLP_WAKE_UP_SRC);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+2
-2
@@ -11,12 +11,12 @@
|
|||||||
|
|
||||||
// LSM6DS3 wakeup threshold: 1 LSB = 7.8 mg at ±2 g FS (±2g range).
|
// LSM6DS3 wakeup threshold: 1 LSB = 7.8 mg at ±2 g FS (±2g range).
|
||||||
#ifndef SLEEP_WAKEUP_THS
|
#ifndef SLEEP_WAKEUP_THS
|
||||||
#define SLEEP_WAKEUP_THS 16 // 0–63
|
#define SLEEP_WAKEUP_THS 6 // 0–63
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// Number of consecutive 26 Hz samples that must exceed the threshold.
|
// Number of consecutive 26 Hz samples that must exceed the threshold.
|
||||||
#ifndef SLEEP_WAKEUP_DUR
|
#ifndef SLEEP_WAKEUP_DUR
|
||||||
#define SLEEP_WAKEUP_DUR 2 // 0–3
|
#define SLEEP_WAKEUP_DUR 1 // 0–3
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// GPIO pin connected to LSM6DS3 INT1.
|
// GPIO pin connected to LSM6DS3 INT1.
|
||||||
|
|||||||
Reference in New Issue
Block a user