Teensy 4.1 Built-in RTC problem

danieltsz

Well-known member
Hi, I'm new to Teensy Boards. I want to migrate my code from Arduino Mega to Teensy 4.1.
One component of my project is using RTC to monitor time for logging and sending data.

I learned that Teensy 4.1 has built-in RTC but I'm encountering some problems with it.
I noticed that every 10 minutes, the function minute() sends the wrong value.
As seen in the attached photo, after 9:10:59, time resets to 9:10:0 then proceeds to 9:11:1.

What do you think I'm doing wrong in my program?

Code:
#include <SPI.h>
#include <SD.h>
File DataLogger;

#include <TimeLib.h>
#define time_offset 8

time_t getTeensyTime() {
  return Teensy3Clock.get();
}

#include "Watchdog_t4.h"
WDT_T4<WDT1> wdt;

#include <InternalTemperature.h>

/////////////////////////////////////////////////////////////////////
//01. General Variables
/////////////////////////////////////////////////////////////////////
char Logfile[23];
char Datafile[20];

String LogFileName = "";
String DataFileName = "";

String sdString = "";

const byte LED_DataLogger = LED_BUILTIN;

int Year = 0;
byte Month = 0;
byte Day = 0;
byte Hour = 0;
byte Minute = 0;
byte Second = 0;

byte PreviousSecond = 0;

char DateTimeStamp[25];

//Temperature
//storage for the measured value of the battery
float mcuTemperature = 0.0;

void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);  //PC
  Serial.setTimeout(100);

  setSyncProvider(getTeensyTime);

  if (timeStatus() != timeSet) {
    Serial.println("Unable to sync with the RTC");
    Serial.flush();
  }

  if (!SD.begin(BUILTIN_SDCARD)) {
    Serial.println(F("SD card Module failed, or not present"));
    Serial.flush();
    while (1)
      ;
  }

  SD.mkdir("INFO");
  SD.mkdir("DATA");
  SD.mkdir("WARNING");
  SD.mkdir("LOGFILE");

  DataLogger.setTimeout(100);

  WDT_timings_t config;
  config.trigger = 5;  /* in seconds, 0->128 */
  config.timeout = 10; /* in seconds, 0->128 */
  wdt.begin(config);
  pinMode(LED_BUILTIN, OUTPUT);
}

void loop() {
  // put your main code here, to run repeatedly:
  Month = month();
  Day = day();
  Year = year();

  Hour = hour();
  Minute = minute();
  Second = second();

  if (Minute % 10 == 0 && Second == 0 && PreviousSecond != Second) {
    SyncTime();

    mcuTemperature = InternalTemperature.readTemperatureC();
    Serial.print("Teensy4.1 Temperature @ ");
    Serial.print(DateTimeStamp);
    Serial.print(": ");
    Serial.print(mcuTemperature);
    Serial.println("°C");

    DataLogger = SD.open(Datafile, FILE_WRITE);
    if (DataLogger) {
      DataLogger.print(DateTimeStamp);
      DataLogger.print(F(" > Temperature   : "));
      DataLogger.println(mcuTemperature);
      DataLogger.close();
    } else {
      Serial.print(F("error opening "));
      Serial.print(Datafile);
      Serial.println();
      Serial.flush();
    }
  }

  if (Second % 5 == 0 && PreviousSecond != Second) {
    wdt.feed(); /* uncomment to feed the watchdog */
  }

  if (PreviousSecond != Second) {
    Serial.print("Date: ");
    Serial.print(Month);
    Serial.print("/");
    Serial.print(Day);
    Serial.print("/");
    Serial.print(Year);
    Serial.print(" ");

    Serial.print("Time: ");
    Serial.print(Hour);
    Serial.print(":");
    Serial.print(Minute);
    Serial.print(":");
    Serial.println(Second);

    if (digitalRead(LED_DataLogger) == LOW) {
      digitalWrite(LED_DataLogger, HIGH);
    } else {
      digitalWrite(LED_DataLogger, LOW);
    }
  }

  PreviousSecond = Second;
}

void SyncTime() {
  sprintf(DateTimeStamp, "%04u/%02u/%02u %02u:%02u:%02u", Year, Month, Day, Hour, Minute, Second);
  sprintf(Logfile, "LOGFILE/%04u%02u%02u.txt", Year, Month, Day);
  sprintf(Datafile, "DATA/%04u%02u%02u.txt", Year, Month, Day);
  //Serial.println(DateTimeStamp);
}
 

Attachments

  • SerialMonitor.PNG
    SerialMonitor.PNG
    8.2 KB · Views: 29
You need to grab the time atomically (probably using now() ) and then extract the seconds, minutes, hours etc. from that value.
The problem is you're calling minute() and then the clock ticks over to the next minute before the call to seconds() occurs.
 
Thank you for the big help.

I just got the idea from the timeTeensy3 example from File>Examples>Time>Timeteensy3
I just finished testing your suggestion about using now() function and I think it works perfectly "now" :D:D.
Thank you very much.
 
Back
Top