int8_t SecondCorMs; //Коррекция времени
#define MS_IN_SECOND 1000L - SecondCorMs
...........
uint32_t msReset = MS_IN_SECOND;
void TickSecondTimer() { //Секундный таймер
if ((uint32_t)(millis() - msReset >= MS_IN_SECOND)) {
if (SecondDev >= 86399ul) {
SecondDev = 0;
ResetDay();
} else SecondDev++;
if (Pump[0].Relay.State) Pump[0].Relay.workTime++;
if (Pump[1].Relay.State) Pump[1].Relay.workTime++;
if (Heat.Relay.State) Heat.Relay.workTime++;
VerifyEditAndSysView();
isFlash = !isFlash;
if (LightLCD > 0) LightLCD--;
do {
msReset += MS_IN_SECOND;
if (msReset < MS_IN_SECOND) break;
} while ((uint32_t)(msReset < (millis() - MS_IN_SECOND)));
}
}
Изначально период был 1000. Но таймер “уплывал” причем сильно. Сделал так как сейчас, т.е. с возможностью коррекции в плюс или минус. Но не пойму почему так не стабильно это работает. Если ставлю +7 в SecondCorMs то часы ( SecondDev++;) за пару суток отстают на пару минут. Поставил +8 вроде как вперед начинают бежать… Не получится более менее стабильного времени таким способом сделать? Не пойму, если на 1 мск сократить, то за сутки 86.4 секунды уйдет? Туплю…
Часовой кварц здесь ни при чём. Тут важна частота резонатора. Кварцев у китайцев нет - только керамика. Однако, для местных поделок вполне. 2000000 BPS вполне, работает.
С таким кодом - неудивительно. Вы писали? Что, например, означает глубокомысленное преобразование (uint32_t) в восьмой и двадцать второй строках? А что вообще делают строки №№ 19-22? Для чего они?
P.S. Если у Вас есть вопросы, я отвечу, но не быстро, мне ещё три+ часа баранку вертеть и сюда я заглядываю во время перекуров
Ну нет. Тему нужно держать в курсе.)
А если серьёзно. Иной раз спишь и всё равно тема крутится в голове… Хотя, может я такой впечатлительный…) Поражаюсь тому как жена спит словно убитая…)
Это весьма грубая коррекция.
Считаем:
При добавлении/убавлении 1 мс она прибавляется/убавляется каждую секунду. В сутках 86400 секунд.
В итоге ±1мс коррекции в сутки получаем ±86.4 секунды.
А тут или я дурак или лыжи не едут. Условие же не выполняется, если не считать случаев с переполнениями. Чую здесь потенциальный косяк, который потом сложно будет отладить.
Спасибо, что обратили внимание. Да, действительно, сейчас увидел, что это не верно. Ибо я условное выражение ((millis() - msReset >= MS_IN_SECOND)) привожу к uint32_t. Скорее всего у меня была проблема с таймером (возможно другая) и я ее решал по скорому… она решилась (видать другим способом) но этот бред остался. И скорее всего я не логическое выражение хотел привести к uint32_t а (millis() - msReset)… Исправлю, точнее уберу, так как работаю с одинаковыми типами…
Ну да. Где-то у гайвера видел, т.н. этот код(алгоритм таймера) с его сайта.
Еще где-то у него было объяснение данного участка, но так как я не гуру в этом, поверил и оставил… Возможно где-то (с другими типами) это нужно, возможно это совсем не нужно. Тогда это вопрос))
Я тоже к этому пришел. Изначально не задумывался. Думал 1 мкс особой роли не сыграет. Даже изначально -100 … +100 коррекцию делал))) А потом посчитал(к удивлению смог)))) шутка) И понял как важна мск во времени глобальном…
Конечно же с учетом, что точного времени я таким кодом не добьюсь, ибо 1 мск убавляешь общее время бежит, прибавляешь отстает…
Да и черт с ней, особой точности не нужно в этом устройстве, неприятно, но не смертельно…