Extender ESP8266 12 F Tiempo de suspensión profunda

0

Me gustaría extender el tiempo máximo de DeepSleep de mi módulo ESP8266 12 F (ejecutando el firmware Arduino ESP8266) a 4 horas. Acabo de descubrir que el tiempo máximo de Deepsleep es de 71 minutos:

Encontré esta breve descripción en este sitio:

  

Una forma común de extender el tiempo de sueño profundo es mantener un contador en NVM (es decir, memoria Flash o RTC), e incrementar el contador cada vez que el dispositivo se activa. Si alcanza un cierto umbral, entonces haga el trabajo, de lo contrario, vuelva a dormir.

¿Entonces estoy tratando de entender cómo debería funcionar esto? Después de Deep Sleep, el módulo ESP8266 12 F se inicia de nuevo en la configuración. Sé que:

bool rtcUserMemoryRead(uint32_t offset, uint32_t *data, size_t size);
bool rtcUserMemoryWrite(uint32_t offset, uint32_t *data, size_t size);

lee y escribe cosas en la memoria del RTC pero no estoy seguro de cómo preparar un contador para que el Módulo entre en suspensión profunda 4 * 3600 segundos (hasta 4 horas):

const int sleepTimeS = 3600;//1 Hour (3600 seconds)    
void loop() { 
do somehting;
ESP.deepSleep(sleepTimeS * 1000000,WAKE_RF_DEFAULT); 
}

¿Cómo ubicaría todo para que el código se ejecute durante el arranque y que quede en suspensión durante 4 horas?

El post de DigitalNinjas lo hizo, tuve que hacer 2 ajustes. Aquí está la versión que funcionó para mí:

// NVM Data
#define RTCMemOffset 10 // arbitrary location
#define MAGIC_NUMBER 55 // used to know if the memory is good and been written to 

    struct
    {
int wakeCount;
bool bFirstTime;
int magicNumber;
    } nvmData;

    nvmData sleepMemory;

    bool bDoneSleeping;

    void setup()
    {
/* Woke up and entered setup */
bDoneSleeping = false;

if(ESP.rtcUserMemoryRead((uint32_t)RTCMemOffset, (uint32_t*) &sleepMemory, sizeof(sleepMemory)))// EDIT: ESP. was missing
{
    if(sleepMemory.magicNumber != MAGIC_NUMBER) // memory got corrupt or this is the first time
    {
        sleepMemory.bFirstTime = true;
        sleepMemory.magicNumber = MAGIC_NUMBER;
        sleepMemory.wakeCount = 0;
        bDoneSleeping = true;// EDIT: Set bDoneSleeping to true so that the code runs on boot up
    }
    else
    {
        sleepMemory.wakeCount += 1; // incrememnt the sleep counter
        sleepMemory.bFirstTime = false;
    }

    if(sleepMemory.wakeCount >= 4) // reset the counter and do whatever else   you need to do since 4 hours have passed
    {
        sleepMemory.wakeCount = 0;
        bDoneSleeping = true;
    }   

   ESP.rtcUserMemoryWrite((uint32_t)RTCMemOffset, (uint32_t*) &sleepMemory, sizeof(sleepMemory)); // write the new values to memory // EDIT: ESP. was missing
}

if(bDoneSleeping)
{
     // Perform tasks
}
else
    // Go back to sleep
    }   
    
pregunta Peter S

1 respuesta

1

Todo lo que están sugiriendo es que mantengas un contador en una memoria no volátil para que puedas seguir la cuenta de cuántas veces se ha despertado el ESP.

A veces desea saber si es la primera vez que se ejecuta la aplicación, de modo que pueda hacer cosas que solo querría hacer en el primer arranque. Puedes usar una bandera booleana para este propósito. Si descubre que no necesita, puede eliminarlo de mi ejemplo. Tenga en cuenta que no compilé ni probé este código, podría tener errores y está destinado únicamente como ejemplo para que pueda comenzar con una solución. Espero que ayude :)

// NVM Data
#define RTCMemOffset 10 // arbitrary location
#define MAGIC_NUMBER 55 // used to know if the memory is good and been written to 

struct
{
    int wakeCount;
    bool bFirstTime;
    int magicNumber;
} nvmData;

nvmData sleepMemory;

bool bDoneSleeping;

void setup()
{
    /* Woke up and entered setup */
    bDoneSleeping = false;

    if(rtcUserMemoryRead((uint32_t)RTCMemOffset, (uint32_t*) &sleepMemory, sizeof(sleepMemory)))
    {
        if(sleepMemory.magicNumber != MAGIC_NUMBER) // memory got corrupt or this is the first time
        {
            sleepMemory.bFirstTime = true;
            sleepMemory.magicNumber = MAGIC_NUMBER;
            sleepMemory.wakeCount = 0;
        }
        else
        {
            sleepMemory.wakeCount += 1; // incrememnt the sleep counter
            sleepMemory.bFirstTime = false;
        }

        if(sleepMemory.wakeCount >= 4) // reset the counter and do whatever else you need to do since 4 hours have passed
        {
            sleepMemory.wakeCount = 0;
            bDoneSleeping = true;
        }   

        rtcUserMemoryWrite((uint32_t)RTCMemOffset, (uint32_t*) &sleepMemory, sizeof(sleepMemory)); // write the new values to memory
    }

    if(bDoneSleeping)
    {
         // Perform tasks
    }
    else
        // Go back to sleep
}   
    
respondido por el DigitalNinja

Lea otras preguntas en las etiquetas