diff --git a/Binaries/OpenLog_Artemis-V10-v19_BETA.bin b/Binaries/OpenLog_Artemis-V10-v19_BETA.bin new file mode 100644 index 0000000..a080b6d Binary files /dev/null and b/Binaries/OpenLog_Artemis-V10-v19_BETA.bin differ diff --git a/Firmware/OpenLog_Artemis/OpenLog_Artemis.ino b/Firmware/OpenLog_Artemis/OpenLog_Artemis.ino index 6c714b6..97d8843 100644 --- a/Firmware/OpenLog_Artemis/OpenLog_Artemis.ino +++ b/Firmware/OpenLog_Artemis/OpenLog_Artemis.ino @@ -221,6 +221,7 @@ unsigned long lastDataLogSyncTime = 0; //Used to record to SD every half second unsigned int totalCharactersPrinted = 0; //Limit output rate based on baud rate and number of characters to print bool takeReading = true; //Goes true when enough time has passed between readings or we've woken from sleep const uint64_t maxUsBeforeSleep = 2000000ULL; //Number of us between readings before sleep is activated. +const uint32_t minSecDeepSleep = 10; // minimum number of seconds to go into Deep Sleep when not sampling. const byte menuTimeout = 15; //Menus will exit/timeout after this number of seconds volatile static bool stopLoggingSeen = false; //Flag to indicate if we should stop logging unsigned long qwiicPowerOnTime = 0; //Used to delay after Qwiic power on to allow sensors to power on, then answer autodetect @@ -532,7 +533,9 @@ void loop() { if ((settings.useGPIO32ForStopLogging == true) && (stopLoggingSeen == true)) // Has the user pressed the stop logging button? { - stopLogging(); + printDebug("GPIO32 'STOP LOGGING' triggered.\r\n"); + if ( settings.deepSleepAlarmSecs != 0 ) sleepUntilWoken(); + else stopLogging(); } triggerEdgeSeen = false; // Clear the trigger seen flag here - just in case another trigger was received while we were logging data to SD card @@ -540,7 +543,7 @@ void loop() { //Go to sleep if the time between readings is greater than maxUsBeforeSleep (2 seconds) and triggering is not enabled if ((settings.useGPIO11ForTrigger == false) && (settings.usBetweenReadings >= maxUsBeforeSleep)) { - goToSleep(); + sleepUntilNextSample(); } } } diff --git a/Firmware/OpenLog_Artemis/lowerPower.ino b/Firmware/OpenLog_Artemis/lowerPower.ino index ad6fdd3..81ed0df 100644 --- a/Firmware/OpenLog_Artemis/lowerPower.ino +++ b/Firmware/OpenLog_Artemis/lowerPower.ino @@ -153,14 +153,29 @@ void powerDown() } } +// go to sleep and wake when it's time to take next sample +void sleepUntilNextSample() +{ + uint32_t msToSleep = (uint32_t)(settings.usBetweenReadings / 1000ULL); + //printDebug("Sleeping " + (String)msToSleep + "ms until next sample.\r\n"); + goToSleep(msToSleep); +} + +// Go to sleep and wake when when deepSleepAlarmSecs timer is up +void sleepUntilWoken() +{ + //printDebug("Sleeping on external signal for " + (String)settings.deepSleepAlarmSecs + "sec.\r\n"); + uint32_t msToSleep = (uint32_t)(settings.deepSleepAlarmSecs * 1000ULL); + goToSleep(msToSleep); +} + //Power everything down and wait for interrupt wakeup -void goToSleep() +void goToSleep(uint32_t msToSleep) { //Counter/Timer 6 will use the 32kHz clock //Calculate how many 32768Hz system ticks we need to sleep for: //sysTicksToSleep = msToSleep * 32768L / 1000 //We need to be careful with the multiply as we will overflow uint32_t if msToSleep is > 131072 - uint32_t msToSleep = (uint32_t)(settings.usBetweenReadings / 1000ULL); uint32_t sysTicksToSleep; if (msToSleep < 131000) { @@ -345,8 +360,10 @@ void wakeFromSleep() { pinMode(PIN_STOP_LOGGING, INPUT_PULLUP); delay(1); // Let the pin stabilize - attachInterrupt(digitalPinToInterrupt(PIN_STOP_LOGGING), stopLoggingISR, FALLING); // Enable the interrupt - stopLoggingSeen = false; // Make sure the flag is clear + attachInterrupt(digitalPinToInterrupt(PIN_STOP_LOGGING), stopLoggingISR, FALLING); // Enable the interrupts + // If we're using deepSleepAlarmSecs and PIN_STOP_LOGGING is still pulled low, we will proabably want to go back to sleep. + if (settings.deepSleepAlarmSecs == 0 || digitalRead(PIN_STOP_LOGGING) == HIGH) stopLoggingSeen = false; // Make sure the flag is clear + else stopLoggingSeen = true; } if (settings.useGPIO11ForTrigger == true) //(This should be redundant. We should not be going to sleep if triggering is enabled?) diff --git a/Firmware/OpenLog_Artemis/menuPower.ino b/Firmware/OpenLog_Artemis/menuPower.ino index 870895f..042f212 100644 --- a/Firmware/OpenLog_Artemis/menuPower.ino +++ b/Firmware/OpenLog_Artemis/menuPower.ino @@ -13,19 +13,26 @@ void menuPower() if (settings.useGPIO32ForStopLogging == true) Serial.println(F("Yes")); else Serial.println(F("No")); + if (settings.deepSleepAlarmSecs == 0) + Serial.println(F("3) Set Deep Sleep wakeup alarm.")); + else + { + Serial.print(F("3) Deep Sleep wakeup timer (s): ")); + Serial.printf("%u\r\n", settings.deepSleepAlarmSecs); + } #if(HARDWARE_VERSION_MAJOR >= 1) - Serial.print(F("3) Power LED During Sleep: ")); + Serial.print(F("4) Power LED During Sleep: ")); if (settings.enablePwrLedDuringSleep == true) Serial.println(F("Enabled")); else Serial.println(F("Disabled")); - Serial.print(F("4) Low Battery Voltage Detection: ")); + Serial.print(F("5) Low Battery Voltage Detection: ")); if (settings.enableLowBatteryDetection == true) Serial.println(F("Enabled")); else Serial.println(F("Disabled")); - Serial.print(F("5) Low Battery Threshold (V): ")); + Serial.print(F("6) Low Battery Threshold (V): ")); Serial.printf("%.2f\r\n", settings.lowBatteryThreshold); - Serial.print(F("6) VIN measurement correction factor: ")); + Serial.print(F("7) VIN measurement correction factor: ")); Serial.printf("%.3f\r\n", settings.vinCorrectionFactor); #endif @@ -58,16 +65,26 @@ void menuPower() settings.logA32 = false; // Disable analog logging on pin 32 } } -#if(HARDWARE_VERSION_MAJOR >= 1) else if (incoming == '3') { - settings.enablePwrLedDuringSleep ^= 1; + Serial.println(F("Please enter RTC wakeup time (sec) when put in deep sleep. 0=disable:")); + uint32_t tempRTCwakeUp = (uint32_t)getDouble(menuTimeout); + if ( tempRTCwakeUp == 0 or tempRTCwakeUp >= minSecDeepSleep ) + settings.deepSleepAlarmSecs = tempRTCwakeUp; + else + Serial.printf("Error: Value must be 0 or >= %u\r\n",minSecDeepSleep); } + // Option 3 will be for RTC wake up alarm time +#if(HARDWARE_VERSION_MAJOR >= 1) else if (incoming == '4') { - settings.enableLowBatteryDetection ^= 1; + settings.enablePwrLedDuringSleep ^= 1; } else if (incoming == '5') + { + settings.enableLowBatteryDetection ^= 1; + } + else if (incoming == '6') { Serial.println(F("Please enter the new low battery threshold:")); float tempBT = (float)getDouble(menuTimeout); //Timeout after x seconds @@ -76,7 +93,7 @@ void menuPower() else settings.lowBatteryThreshold = tempBT; } - else if (incoming == '6') + else if (incoming == '7') { Serial.println(F("Please measure the voltage on the MEAS pin and enter it here:")); float tempCF = (float)getDouble(menuTimeout); //Timeout after x seconds diff --git a/Firmware/OpenLog_Artemis/nvm.ino b/Firmware/OpenLog_Artemis/nvm.ino index 7226341..88188a7 100644 --- a/Firmware/OpenLog_Artemis/nvm.ino +++ b/Firmware/OpenLog_Artemis/nvm.ino @@ -140,6 +140,7 @@ void recordSystemSettingsToFile() settingsFile.println("openNewLogFilesAfter=" + (String)settings.openNewLogFilesAfter); settingsFile.println("vinCorrectionFactor=" + (String)settings.vinCorrectionFactor); settingsFile.println("useGPIO32ForStopLogging=" + (String)settings.useGPIO32ForStopLogging); + settingsFile.println("deepSleepAlarmSecs=" + (String)settings.deepSleepAlarmSecs); settingsFile.println("qwiicBusPullUps=" + (String)settings.qwiicBusPullUps); settingsFile.println("outputSerial=" + (String)settings.outputSerial); settingsFile.println("zmodemStartDelay=" + (String)settings.zmodemStartDelay); @@ -367,6 +368,8 @@ bool parseLine(char* str) { settings.vinCorrectionFactor = d; else if (strcmp(settingName, "useGPIO32ForStopLogging") == 0) settings.useGPIO32ForStopLogging = d; + else if (strcmp(settingName, "deepSleepAlarmSecs") == 0) + settings.deepSleepAlarmSecs = d; else if (strcmp(settingName, "qwiicBusPullUps") == 0) settings.qwiicBusPullUps = d; else if (strcmp(settingName, "outputSerial") == 0) diff --git a/Firmware/OpenLog_Artemis/settings.h b/Firmware/OpenLog_Artemis/settings.h index 465e6ab..1989f15 100644 --- a/Firmware/OpenLog_Artemis/settings.h +++ b/Firmware/OpenLog_Artemis/settings.h @@ -336,6 +336,7 @@ struct struct_settings { unsigned long openNewLogFilesAfter = 0; //Default to 0 (Never) seconds float vinCorrectionFactor = 1.47; //Correction factor for the VIN measurement; to compensate for the divider impedance bool useGPIO32ForStopLogging = false; //If true, use GPIO as a stop logging button + uint32_t deepSleepAlarmSecs = 0; // Number of seconds after going into deep sleep that RTC alarm should wake OLA, 0=disabled uint32_t qwiicBusPullUps = 1; //Default to 1.5k I2C pull-ups - internal to the Artemis bool outputSerial = false; // Output the sensor data on the TX pin uint8_t zmodemStartDelay = 20; // Wait for this many seconds before starting the zmodem file transfer diff --git a/README.md b/README.md index 3e59633..a3e518d 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,13 @@ SparkFun OpenLog Artemis =========================================================== +Changes in my version: + +DONE +* Added uint32_t setting called deepSleepAlarmSecs. When set to 0, nothing changes, but when > 0, it will set an alarm that many seconds into the future whewn entering Deep Sleep. +* Added provision to menuPower for setting deepSleepAlarmSecs +* When waking up, if deepSleepAlarmSecs != 0 and useGPIO32ForStopLogging = true, will set stopLoggingSeen based on PIN_STOP_LOGGING rather than assume false. +TO DO: +* implement RTC alarm when entering Deep Sleep.