#include #include #include #include RtcDS3231 Rtc(Wire); const int ledPin = 17; const int wakeUpPin = 7; const int wakeUpInterrupt = digitalPinToInterrupt(wakeUpPin); volatile uint16_t interuptCount = 0; volatile bool interuptFlag = false; bool Alarmed(); void printDateTime(const RtcDateTime &dt); void ISR_ATTR InteruptServiceRoutine() { // sleep_disable(); // detachInterrupt(wakeUpInterrupt); interuptCount++; interuptFlag = true; } void sleepNow() { // set_sleep_mode(SLEEP_MODE_PWR_DOWN); noInterrupts(); // sleep_enable(); attachInterrupt(wakeUpInterrupt, InteruptServiceRoutine, FALLING); interrupts(); // sleep_cpu(); } void setup() { pinMode(wakeUpPin, INPUT_PULLUP); pinMode(ledPin, OUTPUT); Serial.begin(9660); Rtc.Begin(); RtcDateTime compiled = RtcDateTime(__DATE__, __TIME__); if (!Rtc.IsDateTimeValid()) { if (Rtc.LastError() != 0) { // we have a communications error // see https://www.arduino.cc/en/Reference/WireEndTransmission for // what the number means Serial.print("RTC communications error = "); Serial.println(Rtc.LastError()); } else { Serial.println("RTC lost confidence in the DateTime!"); Rtc.SetDateTime(compiled); } } if (!Rtc.GetIsRunning()) { Serial.println("RTC was not actively running, starting now"); Rtc.SetIsRunning(true); } RtcDateTime now = Rtc.GetDateTime(); if (now < compiled) { Serial.println("RTC is older than compile time! (Updating DateTime)"); Rtc.SetDateTime(compiled); } Rtc.Enable32kHzPin(false); Rtc.SetSquareWavePin(DS3231SquareWavePin_ModeAlarmOne); DS3231AlarmOne alarm1(0, 0, 0, 0, DS3231AlarmOneControl_OncePerSecond); Rtc.SetAlarmOne(alarm1); Rtc.LatchAlarmsTriggeredFlags(); attachInterrupt(wakeUpPin, InteruptServiceRoutine, FALLING); } // void loop() // { // digitalWrite(ledPin, !digitalRead(ledPin)); // Serial.println("interrupred"); // sleepNow(); // } void loop () { if (!Rtc.IsDateTimeValid()) { if (Rtc.LastError() != 0) { // we have a communications error // see https://www.arduino.cc/en/Reference/WireEndTransmission for // what the number means Serial.print("RTC communications error = "); Serial.println(Rtc.LastError()); } else { Serial.println("RTC lost confidence in the DateTime!"); } } RtcDateTime now = Rtc.GetDateTime(); printDateTime(now); Serial.println(); // we only want to show time every 10 seconds // but we want to show responce to the interupt firing for (int timeCount = 0; timeCount < 20; timeCount++) { if (Alarmed()) { Serial.print(">>Interupt Count: "); Serial.print(interuptCount); Serial.println("<<"); digitalWrite(ledPin, !digitalRead(ledPin)); } delay(500); } // sleepNow(); } bool Alarmed() { bool wasAlarmed = false; if (interuptFlag) // check our flag that gets sets in the interupt { wasAlarmed = true; interuptFlag = false; // reset the flag // this gives us which alarms triggered and // then allows for others to trigger again DS3231AlarmFlag flag = Rtc.LatchAlarmsTriggeredFlags(); if (flag & DS3231AlarmFlag_Alarm1) { Serial.println("alarm one triggered"); } if (flag & DS3231AlarmFlag_Alarm2) { Serial.println("alarm two triggered"); } } return wasAlarmed; } #define countof(a) (sizeof(a) / sizeof(a[0])) void printDateTime(const RtcDateTime& dt) { char datestring[20]; snprintf_P(datestring, countof(datestring), PSTR("%02u/%02u/%04u %02u:%02u:%02u"), dt.Month(), dt.Day(), dt.Year(), dt.Hour(), dt.Minute(), dt.Second() ); Serial.print(datestring); } // // CONNECTIONS: // // DS3231 SDA --> SDA // // DS3231 SCL --> SCL // // DS3231 VCC --> 3.3v or 5v // // DS3231 GND --> GND // // SQW ---> (Pin19) Don't forget to pullup (4.7k to 10k to VCC) // /* for software wire use below // #include // must be included here so that Arduino library object file references work // #include // SoftwareWire myWire(SDA, SCL); // RtcDS3231 Rtc(myWire); // for software wire use above */ // /* for normal hardware wire use below */ // #include // must be included here so that Arduino library object file references work // #include // RtcDS3231 Rtc(Wire); // /* for normal hardware wire use above */ // bool Alarmed(); // void printDateTime(const RtcDateTime& dt); // const byte LED = 17; // // Interrupt Pin Lookup Table // // (copied from Arduino Docs) // // // // CAUTION: The interrupts are Arduino numbers NOT Atmel numbers // // and may not match (example, Mega2560 int.4 is actually Atmel Int2) // // this is only an issue if you plan to use the lower level interupt features // // // // Board int.0 int.1 int.2 int.3 int.4 int.5 // // --------------------------------------------------------------- // // Uno, Ethernet 2 3 // // Mega2560 2 3 21 20 [19] 18 // // Leonardo 3 2 0 1 7 // #define RtcSquareWavePin 7 // Mega2560 // #define RtcSquareWaveInterrupt 4 // Mega2560 // // marked volatile so interrupt can safely modify them and // // other code can safely read and modify them // volatile uint16_t interuptCount = 0; // volatile bool interuptFlag = false; // void ISR_ATTR InteruptServiceRoutine() // { // // since this interupted any other running code, // // don't do anything that takes long and especially avoid // // any communications calls within this routine // interuptCount++; // interuptFlag = true; // } // void setup () // { // Serial.begin(9600); // // set the interupt pin to input mode // pinMode(RtcSquareWavePin, INPUT); // //--------RTC SETUP ------------ // // if you are using ESP-01 then uncomment the line below to reset the pins to // // the available pins for SDA, SCL // // Wire.begin(0, 2); // due to limited pins, use pin 0 and 2 for SDA, SCL // Rtc.Begin(); // RtcDateTime compiled = RtcDateTime(__DATE__, __TIME__); // if (!Rtc.IsDateTimeValid()) // { // if (Rtc.LastError() != 0) // { // // we have a communications error // // see https://www.arduino.cc/en/Reference/WireEndTransmission for // // what the number means // Serial.print("RTC communications error = "); // Serial.println(Rtc.LastError()); // } // else // { // Serial.println("RTC lost confidence in the DateTime!"); // Rtc.SetDateTime(compiled); // } // } // if (!Rtc.GetIsRunning()) // { // Serial.println("RTC was not actively running, starting now"); // Rtc.SetIsRunning(true); // } // RtcDateTime now = Rtc.GetDateTime(); // if (now < compiled) // { // Serial.println("RTC is older than compile time! (Updating DateTime)"); // Rtc.SetDateTime(compiled); // } // Rtc.Enable32kHzPin(false); // Rtc.SetSquareWavePin(DS3231SquareWavePin_ModeAlarmBoth); // // Alarm 1 set to trigger every day when // // the hours, minutes, and seconds match // RtcDateTime alarmTime = now + 88; // into the future // DS3231AlarmOne alarm1( // alarmTime.Day(), // alarmTime.Hour(), // alarmTime.Minute(), // alarmTime.Second(), // DS3231AlarmOneControl_HoursMinutesSecondsMatch); // Rtc.SetAlarmOne(alarm1); // // Alarm 2 set to trigger at the top of the minute // DS3231AlarmTwo alarm2( // 0, // 0, // 0, // DS3231AlarmTwoControl_OncePerMinute); // Rtc.SetAlarmTwo(alarm2); // // throw away any old alarm state before we ran // Rtc.LatchAlarmsTriggeredFlags(); // // setup external interupt // attachInterrupt(RtcSquareWaveInterrupt, InteruptServiceRoutine, FALLING); // } // void loop () // { // if (!Rtc.IsDateTimeValid()) // { // if (Rtc.LastError() != 0) // { // // we have a communications error // // see https://www.arduino.cc/en/Reference/WireEndTransmission for // // what the number means // Serial.print("RTC communications error = "); // Serial.println(Rtc.LastError()); // } // else // { // Serial.println("RTC lost confidence in the DateTime!"); // } // } // RtcDateTime now = Rtc.GetDateTime(); // printDateTime(now); // Serial.println(); // // we only want to show time every 10 seconds // // but we want to show responce to the interupt firing // for (int timeCount = 0; timeCount < 20; timeCount++) // { // if (Alarmed()) // { // Serial.print(">>Interupt Count: "); // Serial.print(interuptCount); // Serial.println("<<"); // digitalWrite(LED, !digitalRead(LED)); // } // delay(500); // } // } // bool Alarmed() // { // bool wasAlarmed = false; // if (interuptFlag) // check our flag that gets sets in the interupt // { // wasAlarmed = true; // interuptFlag = false; // reset the flag // // this gives us which alarms triggered and // // then allows for others to trigger again // DS3231AlarmFlag flag = Rtc.LatchAlarmsTriggeredFlags(); // if (flag & DS3231AlarmFlag_Alarm1) // { // Serial.println("alarm one triggered"); // } // if (flag & DS3231AlarmFlag_Alarm2) // { // Serial.println("alarm two triggered"); // } // } // return wasAlarmed; // } // #define countof(a) (sizeof(a) / sizeof(a[0])) // void printDateTime(const RtcDateTime& dt) // { // char datestring[20]; // snprintf_P(datestring, // countof(datestring), // PSTR("%02u/%02u/%04u %02u:%02u:%02u"), // dt.Month(), // dt.Day(), // dt.Year(), // dt.Hour(), // dt.Minute(), // dt.Second() ); // Serial.print(datestring); // } // // #include // // // **** INCLUDES ***** // // #include "LowPower.h" // // // Use pin 2 as wake up pin // // const int wakeUpPin = 7; // // const int ledPin = 17; // // void wakeUp() // // { // // // Just a handler for the pin interrupt. // // } // // void setup() // // { // // // Configure wake up pin as input. // // // This will consumes few uA of current. // // pinMode(wakeUpPin, INPUT); // // } // // void loop() // // { // // // Allow wake up pin to trigger interrupt on low. // // attachInterrupt(digitalPinToInterrupt(wakeUpPin), wakeUp, LOW); // // // Enter power down state with ADC and BOD module disabled. // // // Wake up when wake up pin is low. // // LowPower.powerDown(SLEEP_FOREVER, ADC_OFF, BOD_OFF); // // // Disable external pin interrupt on wake up pin. // // detachInterrupt(digitalPinToInterrupt(wakeUpPin)); // // // Do something here // // // Example: Read sensor, data logging, data transmission. // // pinMode(ledPin, OUTPUT); // // delay(100); // // digitalWrite(ledPin, HIGH); // // delay(100); // // digitalWrite(ledPin, LOW); // // delay(100); // // pinMode(ledPin, INPUT); // // } //