Nie potrzebujesz RTC, aby zbudować zegar: układ ATmega ma cały sprzęt niezbędny do wykonywania zadań samego RTC. Oto jak:
Zdobądź kryształ zegarka 32768 Hz: kup go lub zdemontuj stary zegar. Kryształy te, specjalnie zaprojektowane do utrzymywania czasu, mają wyjątkowo mały dryft temperaturowy. Potrzebujesz także jednego z nich, jeśli chcesz użyć układu RTC.
Skonfiguruj bezpieczniki swojego ATmega, aby uruchomić oscylator RC 8 MHz. To sprawi, że twoja millis()
funkcja będzie okropnie niedokładna, a także zwolni piny XTAL1 i XTAL2.
Podłącz kryształ zegarka do pinów TOSC1 i TOSC2. Są to te same piny, co XTAL1 i XTAL2 (9 i 10 w 328P). Różne nazwy oznaczają różne funkcje.
Skonfiguruj Timer / Licznik 2 do pracy asynchronicznej, normalnego trybu zliczania, preskalera ustawionego na 128 i włącz przerwanie przepełnienia timera.
Teraz otrzymasz przerwanie TIMER2_OVF ze stałą szybkością raz na sekundę. W ISR wystarczy przesunąć wyświetlanie zegara o jedną sekundę. Pomiędzy przerwami możesz wprowadzić MCU w bardzo głęboki sen (tryb uśpienia oszczędzania energii: nic nie działa poza Timerem / Licznikiem 2) i latami działać na kilku ogniwach AA. Oczywiście, chyba że wyświetlacz jest energochłonny.
Zrobiłem dokładnie to, aby zbudować 24-godzinny zegar ścienny jednoręczny . Ten link wskazuje teraz na angielskie tłumaczenie oryginalnej dokumentacji na francuski.
Kalibracja kwarcowa
Jeśli nie skalibrujesz kwarcu, możesz spodziewać się znacznego dryfu, zwykle kilka sekund w tygodniu . Szybkość dryfu zależy od pojemności błądzącej śladów łączących kryształ z MCU. Zasadniczo można go usunąć przez dodanie dodatkowej, precyzyjnie dostrojonej pojemności. Warto zauważyć, że miałbyś ten sam problem z dryfowaniem z RTC.
Jeśli jesteś zadowolony z tego rodzaju dokładności, żyj nim i bądź szczęśliwy. Jeśli jednak zmierzysz dryf, zauważysz, że jest on bardzo stabilny. Następnie możesz łatwo zrekompensować to w oprogramowaniu i osiągnąć dokładność kilku sekund rocznie .
Algorytm korygowania znoszenia jest bardzo prosty. Na podstawie zmierzonego dryfu obliczasz dokładne opóźnienie między przerwaniami, które powinno być bardzo bliskie 10 9 nanosekund, a następnie:
#define ONE_SECOND 1000000000 // in nanoseconds
#define ONE_INTERRUPT 999993482 // for example
ISR(TIMER2_OVF_vect)
{
static uint32_t unaccounted_time;
unaccounted_time += ONE_INTERRUPT;
while (unaccounted_time >= ONE_SECOND) {
advance_display_by_one_second();
unaccounted_time -= ONE_SECOND;
}
}
W powyższym przykładzie kwarc jest nieco zbyt szybki, a oprogramowanie kompensuje „brak” tyknięcia co kilka dni. Gdyby kwarc był zbyt wolny, ten sam kod zamiast tego dwukrotnie zaznaczałby raz na kilka dni.
Tego rodzaju kalibrację można również wykonać dla RTC, ale byłoby to znacznie bardziej złożone, ponieważ RTC zgłasza czas w rozbiciu, który naturalnie nie nadaje się do operacji arytmetycznych.