RTC.cpp and RTC.h files are modified to use datetimeToEpoch and epochToDatetime functions:
RTC.cpp
...
#include <stdio.h>
// Utility functions - local scope only
namespace {
static const int days_in_month[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
static bool is_leap(int year) {
return (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
}
} // namespace
Rtc::~Rtc() {
}
...
int Rtc::getSeconds() {
int year, month, day, hour, minute, second;
int retVal = getTime(year, month, day, hour, minute, second);
if (retVal == 0) {
return second;
}
return -1;
}
/**
* @brief Converts a date and time to Unix epoch seconds.
*
* This utility function calculates the number of seconds since
* January 1, 1970 (the Unix epoch) for the provided date and time.
*
* @param year Year value (e.g., 2025).
* @param month Month value (1–12).
* @param day Day value (1–31).
* @param hour Hour value (0–23).
* @param minute Minute value (0–59).
* @param second Second value (0–59).
* @return Corresponding epoch time in seconds.
*/
time_t Rtc::datetimeToEpoch(int year, int month, int day, int hour, int minute, int second) {
int y = year;
int m = month;
time_t days = 0;
for (int i = 1970; i < y; i++) {
days += is_leap(i) ? 366 : 365;
}
for (int i = 1; i < m; i++) {
days += days_in_month[i - 1];
if (i == 2 && is_leap(y)) {
days += 1;
}
}
days += (day - 1);
return (((days * 24 + hour) * 60 + minute) * 60 + second);
}
/**
* @brief Converts Unix epoch seconds to a date and time.
*
* This utility function breaks down a given epoch timestamp into a
* human-readable calendar date and time.
*
* @param t Epoch time in seconds.
* @param year Reference to store the year.
* @param month Reference to store the month.
* @param day Reference to store the day.
* @param hour Reference to store the hour.
* @param minute Reference to store the minute.
* @param second Reference to store the second.
*/
void Rtc::epochToDatetime(time_t t, int &year, int &month, int &day, int &hour, int &minute,
int &second) {
time_t seconds_in_day = t % 86400;
time_t days = t / 86400;
hour = seconds_in_day / 3600;
minute = (seconds_in_day % 3600) / 60;
second = seconds_in_day % 60;
year = 1970;
while (true) {
int days_in_year = is_leap(year) ? 366 : 365;
if (days >= days_in_year) {
days -= days_in_year;
year++;
} else {
break;
}
}
int m = 0;
while (true) {
int dim = days_in_month[m];
if (m == 1 && is_leap(year)) {
dim++;
}
if (days >= dim) {
days -= dim;
m++;
} else {
break;
}
}
month = m + 1;
day = days + 1;
}
#if !defined(CONFIG_COUNTER_NRF_RTC) // For boards with a dedicated RTC peripheral/driver, we use
// the Zephyr RTC
...
RTC.h
...
int getCalibration(int32_t &calibration);
/** @brief Converts a date and time to a Unix epoch timestamp. */
time_t datetimeToEpoch(int year, int month, int day, int hour, int minute, int second);
/** @brief Converts a Unix epoch timestamp to a date and time. */
void epochToDatetime(time_t t, int &year, int &month, int &day, int &hour, int &minute,
int &second);
private:
RtcAlarmCallback userAlarmCallback = nullptr; /**< User-registered alarm callback. */
void *userAlarmCallbackData = nullptr; /**< User data for alarm callback. */
...
sketch.ino
...
#include <vector>
#include "Arduino_RouterBridge.h"
#include "ArduinoJson.h"
#include "MsgPack.h"
#include "RTC.h"
...
typedef struct PythonDict {
MsgPack::str_t key_time;
int time;
MsgPack::str_t key_datetime;
std::vector<int> datetime;
MSGPACK_DEFINE_MAP(key_time, time, key_datetime, datetime);
} python_dict_t;
...
const char* BUILD_TIMESTAMP = __DATE__ " " __TIME__;
Rtc rtc;
bool rtc_ready = false;
...
python_dict_t get_time_dict() {
int year{}, month{}, day{}, hour{}, minute{}, second{};
time_t time{};
python_dict_t dict = {};
if (rtc_ready) {
rtc.getTime(year, month, day, hour, minute, second);
time = rtc.datetimeToEpoch(year, month, day, hour, minute, second) - 32400;
}
dict.key_time = "time";
dict.time = time;
dict.key_datetime = "datetime";
std::vector<int> datetime = {year, month, day, hour, minute, second};
dict.datetime = datetime;
return dict;
}
void set_time(time_t t) {
int year{}, month{}, day{}, hour{}, minute{}, second{};
if(rtc_ready) {
rtc.epochToDatetime(t, year, month, day, hour, minute, second);
rtc.setTime(year, month, day, hour, minute, second);
}
}
void setup() {
pinMode(LED_BUILTIN, OUTPUT);
Serial.begin();
Bridge.begin();
if (!rtc.begin()) {
Serial.println("RTC not ready!\n");
rtc_ready = false;
} else {
rtc_ready = true;
}
Bridge.provide("get_time_dict", get_time_dict);
...
Bridge.provide("set_time", set_time);
...
}
RTC.zip (8.3 KB) * without examples only RTC.cpp and RTC.h