Buenas!! estoy haciendo pruebas con un programa del compañero IGOR R para bajar el consumo del arduino y la verdad es que es una pasado como usando interrupciones podemos "dormir" al Atmega, he conseguido quitando el micro de la placa y montandolo con el hardware basico bajar el consumo de 15mA a 0,31mA lo que alarga la vida de las baterias para mi aplicación. En el programa original del compañero tiene esta linea: (marco en rojo la diferencia)
PRR=(1<<7)|(0<<6)|(1<<5)|(1<<4)|(1<<3)|(1<<2)|(1<<1)|(1<<0);
yo la he cambiado por
PRR=(1<<7)|(0<<6)|(0<<5)|(1<<4)|(1<<3)|(1<<2)|(1<<1)|(1<<0);
Asi habilito en Timer 0 que es el encargado de las temporizaciones DELAY, si no se modifica el programa se queda esperando en esa linea a que pase el tiempo, pero como esta deshabilitado nunca llega y el programa se queda ahi colgado.
Bueno a lo que iba, cargo el programa del compañero IGOR, que es este:
#include <avr/interrupt.h>
#include <avr/sleep.h>
volatile int cont;
void setup()
{
pinMode(13,OUTPUT);
TCCR2A=0;
TCCR2B=(0<<7)|(0<<6)|(0<<5)|(0<<4)|(0<<3)|(1<<2)|(1<<1)|(1<<0); // Preescaler a clock/1024
TIMSK2=(0<<2)|(0<<1)|(1<<0); // Bit 0.- Overflow
SMCR=(0<<3)|(1<<2)|(1<<1)|(0<<0); //Power Save Mode
}
ISR(TIMER2_OVF_vect)
{
cont++;
}
void loop()
{
sleep_enable();
//Turn off ADC
ADCSRA=0;
// TWI | TIMER2 | TIMER0 | VOID | TIMER1 | SPI | USART | ADC
PRR=(1<<7)|(0<<6)|(0<<5)|(1<<4)|(1<<3)|(1<<2)|(1<<1)|(1<<0); // un "1" apaga el modulo un "0" deja en marcha el modulo
sei();
while (cont<122)
{
//Go to Sleep
sleep_mode();
}
//Disable Sleep
sleep_disable();
//Disable interrupts
cli();
cont=0;
digitalWrite(13,!digitalRead(13));
}
Y añado esta linea => delay(3000); debajo del digitalWrite(13,!digitalRead(13)); el programa hace exactamente lo mismo, sin hacer caso del delay. Googleando he visto que en caso de estar en una interrupcion el delay no funciona y se ha de usar delayMicroseconds, pero lo he probado y tampoco funciona.
He seguido Googleando y al parecer despues e la version 0.18 el daleyMicroseconds dejo de funcionar.
A todo esto y despues de pasarme muchas horas haciendo pruebas, leyendo, googleando, etc.. he caido en que el Delay debería funcionar pues está despues de la inhabilitacion de las interrupciones con sleep_disable(); y cli(); por lo que en teoria debería funcionar normalmente porque no está en una interrupcion.
Este es el codigo de la prueba que estoy haciendo, que es el mismo pero añadiendo el delay(3000); al final
#include <avr/interrupt.h>
#include <avr/sleep.h>
volatile int cont;
void setup()
{
pinMode(13,OUTPUT);
TCCR2A=0;
TCCR2B=(0<<7)|(0<<6)|(0<<5)|(0<<4)|(0<<3)|(1<<2)|(1<<1)|(1<<0); // Preescaler a clock/1024
TIMSK2=(0<<2)|(0<<1)|(1<<0); // Bit 0.- Overflow
SMCR=(0<<3)|(1<<2)|(1<<1)|(0<<0); //Power Save Mode
}
ISR(TIMER2_OVF_vect)
{
cont++;
}
void loop()
{
sleep_enable();
//Turn off ADC
ADCSRA=0;
// TWI | TIMER2 | TIMER0 | VOID | TIMER1 | SPI | USART | ADC
PRR=(1<<7)|(0<<6)|(0<<5)|(1<<4)|(1<<3)|(1<<2)|(1<<1)|(1<<0); // un "1" apaga el modulo un "0" deja en marcha el modulo
sei();
while (cont<122)
{
//Go to Sleep
sleep_mode();
}
//Disable Sleep
sleep_disable();
//Disable interrupts
cli();
cont=0;
digitalWrite(13,!digitalRead(13));
delay(3000);
}
Lo he cargado con arduino 023, 1.0 y 1.0.1 y en ninguno funciona =(