Hello,
I spent a lot of time troubleshooting this problem and I can't seem to figure it out.
What is happening is that when I put the chip to sleep, and then try to wake it up from a button press, it won't wake up unless I hold the button down for more than 4 seconds. HOWEVER, if I remove the one line of code, which is sei(); in the sleep method which executes after it wakes up, then I can wake it up with a simple quick button press. However, without that line of code, my timers don't work and my loop method can never call the sleep method again after it wakes up.
Here is where I got the code for the sleep() method.
Here is my full code:
#include <Arduino.h>
#include <avr/sleep.h>
#include <avr/interrupt.h>
#define BUTTON 3
#define P0 0
#define P1 1
#define P2 2
#define BUTTON_PRESSED digitalRead(BUTTON) == HIGH
ISR(PCINT0_vect) {
// This is called when the interrupt occurs, but I don't need to do anything in it
}
void setPins() {
pinMode(BUTTON,INPUT);
pinMode(P0, OUTPUT);
pinMode(P1, OUTPUT);
pinMode(P2, OUTPUT);
}
void sleep() {
GIMSK |= _BV(PCIE); // Enable Pin Change Interrupts
PCMSK |= _BV(PCINT3); // Use PB3 as interrupt pin
ADCSRA &= ~_BV(ADEN); // ADC off
set_sleep_mode(SLEEP_MODE_PWR_DOWN);
sleep_enable(); // Sets the Sleep Enable bit in the MCUCR Register (SE BIT)
sei(); // Enable interrupts
sleep_cpu(); // sleep
cli(); // Disable interrupts
PCMSK &= ~_BV(PCINT3); // Turn off PB3 as interrupt pin
sleep_disable(); // Clear SE bit
ADCSRA |= _BV(ADEN); // ADC on
sei(); // Enable interrupts <---THIS IS THE PROBLEM
setPins();
}
void allOff(){
digitalWrite(P0, LOW);
digitalWrite(P1, LOW);
digitalWrite(P2, LOW);
delay(10);
}
void pin0() {
digitalWrite(P0, HIGH);
}
void pin1() {
digitalWrite(P1, HIGH);
}
void pin2() {
digitalWrite(P2, HIGH);
}
void setup() {
setPins();
allOff();
}
void loop() {
static int pin = -1;
if (BUTTON_PRESSED) {
unsigned long start = millis();
delay(100);
while(BUTTON_PRESSED) {
if ((millis() - start) > 3000) {
allOff();
delay(3000);
sleep();
pin = -1;
}
}
pin ++;
allOff();
if (pin >= 3) pin = 0;
switch(pin) {
case 0:
pin0();
break;
case 1:
pin1();
break;
case 2:
pin2();
break;
default:
break;
}
delay(1000);
}
}
I'm stumped. I should be able to wake this chip just by a quick press of the button with this code the way it is, but obviously, I'm missing something.
Any input would be appreciated.
Thank you,
Mike