From d8a00c3f3dd9655ca6966cede360f0e88bb2f5e1 Mon Sep 17 00:00:00 2001 From: Damjan Adamic Date: Fri, 2 Sep 2016 20:47:56 +0200 Subject: [PATCH] * Code refactoring for GPS to RTC clock * Enabled GPS adjust RTC option for Horus * Moved sensor ID to the right to allow display of GPS date/time in Telemetry screen --- radio/src/gui/480x272/model_telemetry.cpp | 7 +-- radio/src/gui/480x272/radio_setup.cpp | 6 +++ radio/src/rtc.cpp | 35 +++++++++++++ radio/src/rtc.h | 51 ++++++++++--------- .../targets/common/arm/stm32/rtc_driver.cpp | 2 +- radio/src/targets/gruvin9x/rtc_driver.cpp | 2 +- radio/src/targets/sky9x/rtc_driver.cpp | 2 +- radio/src/targets/sky9x/rtc_ds3231_driver.cpp | 2 +- radio/src/telemetry/telemetry_sensors.cpp | 23 +-------- 9 files changed, 77 insertions(+), 53 deletions(-) diff --git a/radio/src/gui/480x272/model_telemetry.cpp b/radio/src/gui/480x272/model_telemetry.cpp index a9c113a15..4f0e8a009 100644 --- a/radio/src/gui/480x272/model_telemetry.cpp +++ b/radio/src/gui/480x272/model_telemetry.cpp @@ -75,6 +75,7 @@ enum MenuModelTelemetryFrskyItems { #define TELEM_COL2 200 #define TELEM_COL3 275 #define TELEM_COL4 350 +#define TELEM_COL5 425 #define IF_FAS_OFFSET(x) x, #define IS_RANGE_DEFINED(k) (g_model.frsky.channels[k].ratio > 0) @@ -443,11 +444,11 @@ bool menuModelTelemetryFrsky(event_t event) // Spektrum does not (yet?) really support multiple sensor of the same type. But a lot of // different sensor display the same information (e.g. voltage, capacity). Show the id // of the sensor in the overview to ease figuring out what sensors belong together - lcdDrawHexNumber(TELEM_COL4, y, sensor->id, LEFT); + lcdDrawHexNumber(TELEM_COL5, y, sensor->id, LEFT); } else #endif if (sensor->type == TELEM_TYPE_CUSTOM && !g_model.ignoreSensorIds) { - lcdDrawNumber(TELEM_COL4, y, sensor->instance, LEFT); + lcdDrawNumber(TELEM_COL5, y, sensor->instance, LEFT); } if (attr) { s_editMode = 0; @@ -477,7 +478,7 @@ bool menuModelTelemetryFrsky(event_t event) lcdDrawText(MENUS_MARGIN_LEFT, y, STR_TELEMETRY_SENSORS); lcdDrawText(TELEM_COL2, y, STR_VALUE, 0); if (!g_model.ignoreSensorIds && !IS_SPEKTRUM_PROTOCOL()) { - lcdDrawText(TELEM_COL4, y, STR_ID, 0); + lcdDrawText(TELEM_COL5, y, STR_ID, 0); } break; diff --git a/radio/src/gui/480x272/radio_setup.cpp b/radio/src/gui/480x272/radio_setup.cpp index c1b249a44..b01a60dc3 100644 --- a/radio/src/gui/480x272/radio_setup.cpp +++ b/radio/src/gui/480x272/radio_setup.cpp @@ -74,6 +74,7 @@ enum menuRadioSetupItems { // CASE_SPLASH_PARAM(ITEM_SETUP_DISABLE_SPLASH) CASE_GPS(ITEM_SETUP_LABEL_GPS) CASE_GPS(ITEM_SETUP_TIMEZONE) + CASE_GPS(ITEM_SETUP_ADJUST_RTC) CASE_GPS(ITEM_SETUP_GPSFORMAT) CASE_PXX(ITEM_SETUP_COUNTRYCODE) ITEM_SETUP_LANGUAGE, @@ -417,6 +418,11 @@ bool menuRadioSetup(event_t event) if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.timezone, -12, 12); break; + case ITEM_SETUP_ADJUST_RTC: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_ADJUST_RTC); + g_eeGeneral.adjustRTC = editCheckBox(g_eeGeneral.adjustRTC, RADIO_SETUP_2ND_COLUMN, y, attr, event ) ; + break; + case ITEM_SETUP_GPSFORMAT: lcdDrawText(MENUS_MARGIN_LEFT, y, STR_GPSCOORD); g_eeGeneral.gpsFormat = editChoice(RADIO_SETUP_2ND_COLUMN, y, STR_GPSFORMAT, g_eeGeneral.gpsFormat, 0, 1, attr, event); diff --git a/radio/src/rtc.cpp b/radio/src/rtc.cpp index ee3702fea..a34988eb2 100644 --- a/radio/src/rtc.cpp +++ b/radio/src/rtc.cpp @@ -486,3 +486,38 @@ void gettime(struct gtm * tm) } +#define RTC_ADJUST_PERIOD 60 // how often RTC is checked for accuracy [seconds] +#define RTC_ADJUST_TRESHOLD 20 // how much clock must differ before adjustment is made [seconds] +/* + Changes RTC date/time to the given date/time if: + * RTC_ADJUST_PERIOD seconds have elapsed from the last time this function adjusted the RTC clock + * AND if actual RTC clock differs from the given clock by more than RTC_ADJUST_TRESHOLD seconds + * Function does nothing for a minute around midnight, where date change could produce erroneous result +*/ +uint8_t rtcAdjust(uint16_t year, uint8_t mon, uint8_t day, uint8_t hour, uint8_t min, uint8_t sec) +{ + static tmr10ms_t lastRtcAdjust = 0; + if ((get_tmr10ms()-lastRtcAdjust) > (RTC_ADJUST_PERIOD*100)) { + lastRtcAdjust = get_tmr10ms(); + + struct gtm t; + gettime(&t); + if ((hour == 0 && min == 0) || (hour == 23 && min == 59)) return 0; + + if (t.tm_year != (year-1900) || t.tm_mon != (mon-1) || t.tm_mday != day || + (abs((t.tm_hour-hour)*3600 + (t.tm_min-min)*60 + (t.tm_sec-sec)) > RTC_ADJUST_TRESHOLD)) { + // we adjust RTC only if difference is > 20 seconds + t.tm_year = year - 1900; + t.tm_mon = mon - 1; + t.tm_mday = day; + t.tm_hour = hour; + t.tm_min = min; + t.tm_sec = sec; + g_rtcTime = gmktime(&t); // update local timestamp and get wday calculated + rtcSetTime(&t); + TRACE("RTC clock adjusted to %04d-%02d-%02d %02d:%02d:%02d", year, mon, day, hour, min, sec); + return 1; + } + } + return 0; +} diff --git a/radio/src/rtc.h b/radio/src/rtc.h index b8a236b7e..efbe8f3fb 100644 --- a/radio/src/rtc.h +++ b/radio/src/rtc.h @@ -1,25 +1,25 @@ -/* - * Copyright (C) OpenTX - * - * Based on code named - * th9x - http://code.google.com/p/th9x - * er9x - http://code.google.com/p/er9x - * gruvin9x - http://code.google.com/p/gruvin9x - * - * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#ifndef _RTC_H_ -#define _RTC_H_ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#ifndef _RTC_H_ +#define _RTC_H_ #include @@ -44,15 +44,16 @@ extern gtime_t g_rtcTime; extern uint8_t g_ms100; // global to allow time set function to reset to zero void rtcInit(); +void rtcSetTime(const struct gtm * tm); +gtime_t gmktime (struct gtm *tm); +uint8_t rtcAdjust(uint16_t year, uint8_t mon, uint8_t day, uint8_t hour, uint8_t min, uint8_t sec); #if defined(__cplusplus) && !defined(SIMU) extern "C" { #endif -void rtcSetTime(struct gtm * tm); void gettime(struct gtm * tm); -gtime_t gmktime (struct gtm *tm); #if defined(__cplusplus) && !defined(SIMU) } #endif -#endif // _RTC_H_ +#endif // _RTC_H_ diff --git a/radio/src/targets/common/arm/stm32/rtc_driver.cpp b/radio/src/targets/common/arm/stm32/rtc_driver.cpp index 2807b1add..0c828adc4 100644 --- a/radio/src/targets/common/arm/stm32/rtc_driver.cpp +++ b/radio/src/targets/common/arm/stm32/rtc_driver.cpp @@ -20,7 +20,7 @@ #include "opentx.h" -void rtcSetTime(struct gtm * t) +void rtcSetTime(const struct gtm * t) { RTC_TimeTypeDef RTC_TimeStruct; RTC_DateTypeDef RTC_DateStruct; diff --git a/radio/src/targets/gruvin9x/rtc_driver.cpp b/radio/src/targets/gruvin9x/rtc_driver.cpp index c1a2f6fee..337a4a908 100644 --- a/radio/src/targets/gruvin9x/rtc_driver.cpp +++ b/radio/src/targets/gruvin9x/rtc_driver.cpp @@ -263,7 +263,7 @@ void rtcGetTime(struct gtm * utm) utm->tm_wday = rtc.wday - 1; } -void rtcSetTime(struct gtm * t) +void rtcSetTime(const struct gtm * t) { g_rtcTime = gmktime(t); // update local timestamp and get wday calculated g_ms100 = 0; // start of next second begins now diff --git a/radio/src/targets/sky9x/rtc_driver.cpp b/radio/src/targets/sky9x/rtc_driver.cpp index bd1c6c79f..59ab29eb0 100644 --- a/radio/src/targets/sky9x/rtc_driver.cpp +++ b/radio/src/targets/sky9x/rtc_driver.cpp @@ -236,7 +236,7 @@ struct t_i2cTime uint8_t Time[7] ; } I2CTime ; -void rtcSetTime(struct gtm * t) +void rtcSetTime(const struct gtm * t) { g_rtcTime = gmktime(t); // update local timestamp and get wday calculated g_ms100 = 0; // start of next second begins now diff --git a/radio/src/targets/sky9x/rtc_ds3231_driver.cpp b/radio/src/targets/sky9x/rtc_ds3231_driver.cpp index 3f1b41708..fcb2bf387 100644 --- a/radio/src/targets/sky9x/rtc_ds3231_driver.cpp +++ b/radio/src/targets/sky9x/rtc_ds3231_driver.cpp @@ -60,7 +60,7 @@ void writeRtc(gtm* ptr) i2cWriteBuffer(DS3231_I2C_ADDR, read_buffer, 1, buffer, 7); } -void rtcSetTime(struct gtm * t) +void rtcSetTime(const struct gtm * t) { writeRtc(t); } diff --git a/radio/src/telemetry/telemetry_sensors.cpp b/radio/src/telemetry/telemetry_sensors.cpp index 67b7a6ad3..374c8e062 100644 --- a/radio/src/telemetry/telemetry_sensors.cpp +++ b/radio/src/telemetry/telemetry_sensors.cpp @@ -76,22 +76,12 @@ void TelemetryItem::setValue(const TelemetrySensor & sensor, int32_t val, uint32 else if (unit == UNIT_DATETIME) { uint32_t data = uint32_t(newVal); if (data & 0x000000ff) { - datetime.year = (uint16_t) ((data & 0xff000000) >> 24); + datetime.year = (uint16_t) ((data & 0xff000000) >> 24) + 2000; datetime.month = (uint8_t) ((data & 0x00ff0000) >> 16); datetime.day = (uint8_t) ((data & 0x0000ff00) >> 8); if (datetime.year != 0) { datetime.datestate = 1; } -#if defined(RTCLOCK) - if (g_eeGeneral.adjustRTC && (datetime.datestate == 1)) { - struct gtm t; - gettime(&t); - t.tm_year = datetime.year+4; - t.tm_mon = datetime.month-1; - t.tm_mday = datetime.day; - rtcSetTime(&t); - } -#endif } else { datetime.hour = ((uint8_t) ((data & 0xff000000) >> 24) + g_eeGeneral.timezone + 24) % 24; @@ -102,16 +92,7 @@ void TelemetryItem::setValue(const TelemetrySensor & sensor, int32_t val, uint32 } #if defined(RTCLOCK) if (g_eeGeneral.adjustRTC && datetime.datestate == 1) { - struct gtm t; - gettime(&t); - if (abs((t.tm_hour-datetime.hour)*3600 + (t.tm_min-datetime.min)*60 + (t.tm_sec-datetime.sec)) > 20) { - // we adjust RTC only if difference is > 20 seconds - t.tm_hour = datetime.hour; - t.tm_min = datetime.min; - t.tm_sec = datetime.sec; - g_rtcTime = gmktime(&t); // update local timestamp and get wday calculated - rtcSetTime(&t); - } + rtcAdjust(datetime.year, datetime.month, datetime.day, datetime.hour, datetime.min, datetime.sec); } #endif }