mirror of https://github.com/arendst/Tasmota.git
Merge pull request #16847 from LeonPoon/development
Support nanos in rtc for sync from ntp
This commit is contained in:
commit
0be740850a
|
@ -158,6 +158,7 @@ RTC_NOINIT_ATTR TRtcSettings RtcDataSettings;
|
|||
#endif // ESP32
|
||||
|
||||
struct TIME_T {
|
||||
uint32_t nanos;
|
||||
uint8_t second;
|
||||
uint8_t minute;
|
||||
uint8_t hour;
|
||||
|
|
|
@ -43,10 +43,12 @@ struct RTC {
|
|||
uint32_t standard_time = 0;
|
||||
uint32_t midnight = 0;
|
||||
uint32_t restart_time = 0;
|
||||
uint32_t nanos = 0;
|
||||
uint32_t millis = 0;
|
||||
// uint32_t last_sync = 0;
|
||||
int32_t time_timezone = 0;
|
||||
bool time_synced = false;
|
||||
bool last_synced = false;
|
||||
bool midnight_now = false;
|
||||
bool user_time_entry = false; // Override NTP by user setting
|
||||
} Rtc;
|
||||
|
@ -235,11 +237,14 @@ uint32_t RtcMillis(void) {
|
|||
return (millis() - Rtc.millis) % 1000;
|
||||
}
|
||||
|
||||
void BreakTime(uint32_t time_input, TIME_T &tm) {
|
||||
void BreakNanoTime(uint32_t time_input, uint32_t time_nanos, TIME_T &tm) {
|
||||
// break the given time_input into time components
|
||||
// this is a more compact version of the C library localtime function
|
||||
// note that year is offset from 1970 !!!
|
||||
|
||||
time_input += time_nanos / 1000000000U;
|
||||
tm.nanos = time_nanos % 1000000000U;
|
||||
|
||||
uint8_t year;
|
||||
uint8_t month;
|
||||
uint8_t month_length;
|
||||
|
@ -290,6 +295,10 @@ void BreakTime(uint32_t time_input, TIME_T &tm) {
|
|||
tm.valid = (time_input > START_VALID_TIME); // 2016-01-01
|
||||
}
|
||||
|
||||
void BreakTime(uint32_t time_input, TIME_T &tm) {
|
||||
BreakNanoTime(time_input, 0, tm);
|
||||
}
|
||||
|
||||
uint32_t MakeTime(TIME_T &tm) {
|
||||
// assemble time elements into time_t
|
||||
// note year argument is offset from 1970
|
||||
|
@ -403,6 +412,7 @@ void RtcSecond(void) {
|
|||
mutex = true;
|
||||
|
||||
Rtc.time_synced = false;
|
||||
Rtc.last_synced = true;
|
||||
last_sync = Rtc.utc_time;
|
||||
|
||||
if (Rtc.restart_time == 0) {
|
||||
|
@ -420,6 +430,12 @@ void RtcSecond(void) {
|
|||
TasmotaGlobal.rules_flag.time_set = 1;
|
||||
}
|
||||
} else {
|
||||
if (Rtc.last_synced) {
|
||||
Rtc.last_synced = false;
|
||||
uint32_t nanos = Rtc.nanos + (millis() - Rtc.millis) * 1000000U;
|
||||
Rtc.utc_time += nanos / 1000000000U;
|
||||
Rtc.nanos = nanos % 1000000000U;
|
||||
} else
|
||||
Rtc.utc_time++; // Increment every second
|
||||
}
|
||||
Rtc.millis = millis();
|
||||
|
@ -442,7 +458,7 @@ void RtcSecond(void) {
|
|||
}
|
||||
}
|
||||
|
||||
BreakTime(Rtc.local_time, RtcTime);
|
||||
BreakNanoTime(Rtc.local_time, Rtc.nanos, RtcTime);
|
||||
if (RtcTime.valid) {
|
||||
if (!Rtc.midnight) {
|
||||
Rtc.midnight = Rtc.local_time - (RtcTime.hour * 3600) - (RtcTime.minute * 60) - RtcTime.second;
|
||||
|
|
|
@ -878,13 +878,15 @@ void WifiPollNtp() {
|
|||
|
||||
AddLog(LOG_LEVEL_DEBUG_MORE, PSTR("NTP: Sync time..."));
|
||||
ntp_run_time = millis();
|
||||
uint32_t ntp_time = WifiGetNtp();
|
||||
uint64_t ntp_nanos = WifiGetNtp();
|
||||
uint32_t ntp_time = ntp_nanos / 1000000000;
|
||||
ntp_run_time = (millis() - ntp_run_time) / 1000;
|
||||
// AddLog(LOG_LEVEL_DEBUG, PSTR("NTP: Runtime %d"), ntp_run_time);
|
||||
if (ntp_run_time < 5) { ntp_run_time = 0; } // DNS timeout is around 10s
|
||||
|
||||
if (ntp_time > START_VALID_TIME) {
|
||||
Rtc.utc_time = ntp_time;
|
||||
Rtc.nanos = ntp_nanos % 1000000000;
|
||||
ntp_sync_minute = 60; // Sync so block further requests
|
||||
RtcSync("NTP");
|
||||
} else {
|
||||
|
@ -893,7 +895,7 @@ void WifiPollNtp() {
|
|||
}
|
||||
}
|
||||
|
||||
uint32_t WifiGetNtp(void) {
|
||||
uint64_t WifiGetNtp(void) {
|
||||
static uint8_t ntp_server_id = 0;
|
||||
|
||||
// AddLog(LOG_LEVEL_DEBUG, PSTR("NTP: Start NTP Sync %d ..."), ntp_server_id);
|
||||
|
@ -983,7 +985,13 @@ uint32_t WifiGetNtp(void) {
|
|||
ntp_server_id++; // Next server next time
|
||||
return 0;
|
||||
}
|
||||
return secs_since_1900 - 2208988800UL;
|
||||
|
||||
uint32_t highWord = word(packet_buffer[44], packet_buffer[45]);
|
||||
uint32_t lowWord = word(packet_buffer[46], packet_buffer[47]);
|
||||
|
||||
uint32_t currentNano = (((uint64_t)(highWord << 16 | lowWord)) * 1000000000) >> 32;
|
||||
|
||||
return (((uint64_t) secs_since_1900) - 2208988800UL) * 1000000000 + currentNano;
|
||||
}
|
||||
delay(10);
|
||||
}
|
||||
|
|
|
@ -987,9 +987,12 @@ bool CmndTM1637Clock(void)
|
|||
\*********************************************************************************************/
|
||||
void TM1637ShowTime()
|
||||
{
|
||||
uint8_t hr = RtcTime.hour;
|
||||
uint8_t mn = RtcTime.minute;
|
||||
uint8_t sc = RtcTime.second;
|
||||
struct TIME_T t = RtcTime;
|
||||
BreakNanoTime(Rtc.local_time, Rtc.nanos + (millis() - Rtc.millis) * 1000000, t);
|
||||
uint8_t hr = t.hour;
|
||||
uint8_t mn = t.minute;
|
||||
uint8_t sc = t.second;
|
||||
uint16_t ms = t.nanos / 1000000;
|
||||
|
||||
if (!TM1637Data.clock_24)
|
||||
{
|
||||
|
@ -1009,12 +1012,14 @@ void TM1637ShowTime()
|
|||
|
||||
if (TM1637 == TM1637Data.display_type)
|
||||
{
|
||||
uint8_t colon = ms > 500? 0: 128;
|
||||
uint8_t rawBytes[1];
|
||||
for (uint32_t i = 0; i < 4; i++)
|
||||
uint8_t width = Settings->display_width >= 6? 6: 4;
|
||||
for (uint32_t i = 0; i < width; i++)
|
||||
{
|
||||
rawBytes[0] = tm1637display->encode(tm[i]);
|
||||
if ((millis() % 1000) > 500 && (i == 1))
|
||||
rawBytes[0] = rawBytes[0] | 128;
|
||||
if (i == 1 || (i == 3 && width > 4))
|
||||
rawBytes[0] = rawBytes[0] | colon;
|
||||
tm1637display->printRaw(rawBytes, 1, TM1637Data.digit_order[i]);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue