OK, well my process of discovery continues with this new clock.
One thing that thew me - in addition to the bounds checking issue above is that in all the example code there is this line in setup:
// Reset the AB1805 configuration to default values
ab1805.resetConfig();
In the API documentation we get this:
and on the Github page, the following:

But, what I did not infer - and in hindsight shame on me. Is that this line resets the RTC clock to Unix Time = 0. If you are in a connected state, this is not that big a deal as the RTC example code has a test for whether the RTC is set or not. However, in my use case, the device was not connecting to the Particle cloud overnight. So, the clock would get reset and the device would never realize it was time to wake in the morning as the clock was being reset over and over again.
Here is some example code that cycles through the three different sleep states. You can see the impact of this line by commenting out the ab1805.resetConfig() line.
/*
* Project AB1805-Sleep-Test
* Description: Test the sleep modes and the interaction with the clock
* Author: Chip McClelland
* Date: 12-3-20
*/
#include "AB1805_RK.h"
SYSTEM_THREAD(ENABLED);
SYSTEM_MODE(MANUAL);
SerialLogHandler logHandler;
AB1805 ab1805(Wire);
unsigned long lastTestTimeStamp;
unsigned long timeBetweenTests = 10000;
bool doSleep = false;
bool doWaitForTime = false;
int whichTest = 0;
time_t currentTime;
void setup() {
// Optional: Enable to make it easier to see debug USB serial messages at startup
waitFor(Serial.isConnected, 15000);
delay(1000);
// The sample board has D8 connected to FOUT for wake interrupts
ab1805.withFOUT(D8).setup();
// Note whether the RTC is set before calling resetConfig() as this will make
// isRTCSet return false.
bool rtcSet = ab1805.isRTCSet();
if (!rtcSet) {
Log.info("RTC not set - will connect to the Particle cloud");
Particle.connect();
doWaitForTime = true;
doSleep = false;
}
// Reset the AB1805 configuration to default values - comment this out to keep time between reboots.
ab1805.resetConfig(); // Note! This line also resets the clock so you loose your time sync.
// Enable watchdog
ab1805.setWDT(AB1805::WATCHDOG_MAX_SECONDS);
// The wakeReason is set during setup() so it's safe to call it after resetConfig.
AB1805::WakeReason wakeReason = ab1805.getWakeReason();
if (wakeReason == AB1805::WakeReason::DEEP_POWER_DOWN) {
Log.info("woke from DEEP_POWER_DOWN");
}
else
if (wakeReason == AB1805::WakeReason::ALARM) {
// We were wakened by the alarm
Log.info("woke by alarm (periodic interrupt)");
}
if (EEPROM.read(0) == 5) whichTest = 3; // Coming back from HIBERNATE test
Log.info("Startup complete - beginning tests");
ab1805.getRtcAsTime(currentTime);
Log.info(Time.timeStr(currentTime));
}
void loop() {
// Be sure to call ab1805.loop() on every call to loop()
ab1805.loop();
if ((millis() - lastTestTimeStamp) > timeBetweenTests && !doWaitForTime) doSleep = true;
if (doSleep) {
SystemSleepConfiguration config;
switch (whichTest) {
case 0:
// Be sure to stop the watchdog timer before going to sleep!
ab1805.stopWDT();
// The delay is only so the Log.info will go out by serial. It's not
// necessary for the functioning of sleep itself.
Log.info("Going into Stop Mode Sleep");
delay(100);
ab1805.interruptCountdownTimer(10,false);
config.mode(SystemSleepMode::STOP)
.gpio(D8, FALLING);
System.sleep(config);
break;
case 1:
// Be sure to stop the watchdog timer before going to sleep!
ab1805.stopWDT();
// The delay is only so the Log.info will go out by serial. It's not
// necessary for the functioning of sleep itself.
Log.info("Going into Ultra Low Power Sleep");
delay(100);
ab1805.interruptCountdownTimer(10,false);
config.mode(SystemSleepMode::ULTRA_LOW_POWER)
.gpio(D8, FALLING);
System.sleep(config);
break;
case 2:
// Be sure to stop the watchdog timer before going to sleep!
ab1805.stopWDT();
EEPROM.write(0,5); // Since we will reboot - putting in a flag
// The delay is only so the Log.info will go out by serial. It's not
// necessary for the functioning of sleep itself.
Log.info("Going into Hibernation Sleep");
delay(100);
ab1805.interruptCountdownTimer(10,false);
config.mode(SystemSleepMode::HIBERNATE)
.gpio(D8, FALLING);
System.sleep(config);
break;
case 3:
Log.info("Sleep Tests Complete");
EEPROM.write(0,0);
break;
}
doSleep = false;
lastTestTimeStamp = millis();
if (whichTest < 3) whichTest++;
}
if (doWaitForTime && ab1805.isRTCSet()) { // We got the time we can disconnect
doWaitForTime = false;
doSleep = true;
lastTestTimeStamp = millis();
Log.info("Clock is set - disconnecting");
ab1805.getRtcAsTime(currentTime);
Log.info(Time.timeStr(currentTime));
Particle.disconnect();
}
}
I hope this is helpful and I will keep sharing code as I get more comfortable with the AB1805.
Thanks, Chip