Hello everyone,
I ran into a strange problem using two libraries, which seemingly have no interaction, but behave not as intended. The libraries in question are
- <avr/sleep.h> and <avr/wdt.h>
- <SoftwareSerial.h>
I condensed my code to visualize the problem. Tested on Arduino Nano (Atmega 328,Old Bootloader
#include <Arduino.h>
// #include <Logger.h>
// bool DEBUGLOG = true;
#include<SoftwareSerial.h>
#include <avr/sleep.h>
#include <avr/wdt.h>
#define CORE_POWER_INTERRUPT 0x0A
#define CORE_POWER_WAKEUP 0x0B
#define CORE_POWER_NORMAL 0x0C
#define CORE_POWER_CALCULATION 0x0D
SoftwareSerial SSERIAL = SoftwareSerial(2,3);
void setup() {
Serial.begin(9600);
SSERIAL = SoftwareSerial(3,4);
SSERIAL.begin(115200);
Serial.println("--- Lowpower ---");
delay(1000);
}
uint8_t TIMEOUT_MULTIPLIER = 1;
uint8_t CORE_POWER_STATUS = CORE_POWER_NORMAL;
void wakeupLoop() {
Serial.println("wakeupX");
delay(1500);
CORE_POWER_STATUS = CORE_POWER_NORMAL;
}
void interruptLoop() {
Serial.println("interrupt");
delay(5000);
CORE_POWER_STATUS = CORE_POWER_NORMAL;
}
void calculationLoop() {
Serial.println("calc");
CORE_POWER_STATUS = CORE_POWER_NORMAL;
}
// watchdog interrupt
ISR (WDT_vect)
{
wdt_disable(); // disable watchdog
} // end of WDT_vect
void lowPowerMode_Timer() {
for(uint8_t i=0;i<TIMEOUT_MULTIPLIER;i++) {
Serial.print("Timer_M = "); Serial.println(TIMEOUT_MULTIPLIER);
// Serial.print("M= "); Serial.println(i);
delay(150);
// disable ADC
ADCSRA = 0;
// clear various "reset" flags
MCUSR = 0;
// allow changes, disable reset
WDTCSR = bit (WDCE) | bit (WDE);
// set interrupt mode and an interval
WDTCSR = bit (WDIE) | bit (WDP3) | bit (WDP0); // set WDIE, and 8 seconds delay
wdt_reset(); // pat the dog
set_sleep_mode (SLEEP_MODE_PWR_DOWN);
noInterrupts (); // timed sequence follows
sleep_enable();
// turn off brown-out enable in software
MCUCR = bit (BODS) | bit (BODSE);
MCUCR = bit (BODS);
interrupts (); // guarantees next instruction executed
sleep_cpu ();
}
sleep_disable();
CORE_POWER_STATUS = CORE_POWER_WAKEUP;
Serial.println("\tWakeup");
// cancel sleep a
}
void loop() {
switch(CORE_POWER_STATUS) {
case CORE_POWER_WAKEUP: {
wakeupLoop();
break; }
case CORE_POWER_INTERRUPT: {
interruptLoop();
break;}
case CORE_POWER_CALCULATION: {
calculationLoop();
break; }
default: {
// Serial.println("empty");
break; }
}
lowPowerMode_Timer();
}
Expected Behavior: 8s sleep
Result: Sleep mode is entered, but the device immediately wakes up.
Changing the setup()
instruction and removing SSERIAL.begin(115200);
void setup() {
Serial.begin(9600);
// SSERIAL = SoftwareSerial(3,4);
SSERIAL.begin(115200);
Serial.println("--- Lowpower ---");
delay(1000);
}
OR removing SSERIAL = SoftwareSerial(3,4);
void setup() {
Serial.begin(9600);
SSERIAL = SoftwareSerial(3,4);
// SSERIAL.begin(115200);
Serial.println("--- Lowpower ---");
delay(1000);
}
results in the correct sleeping time (!). Using both commands results in the strange behavior.
I can not find a logical connection between these functions?