Kampis Elektroecke

XMega – RTC

XMega Blockdiagramm

Einige der XMega Chips sind mit einer internen RTC (Real-Time Clock) ausgestattet, welche für sehr präzise Zeitmessungen verwendet werden kann. Hierfür wird ein 32 kHz Quarz an den Pins TOSC1 und TOSC2 (PQ1 – Pin 85 und PQ0 – Pin 84) benötigt, welches ggf. bei den Entwicklungsboards noch angelötet werden muss. Zusätzlich kann diese RTC auch noch über eine externe Batterie versorgt werden, sodass die RTC auch bei Verlust der Versorgungsspannung weiterarbeiten kann.

RTC initialisieren:

Da für die RTC ein zweites Quarz benutzt wird, muss das Quarz am Clocksystem noch aktiviert werden. Dazu wird als erstes mit

der externe 32 kHz Oszillator zugeschaltet und anschließend in den Low Power Mode versetzt. Anschließend wird der Oszillator aktiviert:

Um dem Oszillator genug Zeit zum einschwingen zu geben, wird das Programm solange angehalten bis durch ein Bit im Statusregister signalisiert wird das der Oszillator bereit ist. Dieses Bit wird wie folgt abgefragt:

Der letzte Schritt besteht darin, den Takt auf 1024 kHz zu senken und die RTC zu aktivieren. Dies geschieht so:

RTC konfigurieren:

Da die Taktquelle für die RTC nun fertig initialisiert ist, muss nur noch die RTC eingestellt werden. Als erstes wird mit

das Periodenregister der RTC auf 1023 gestellt. Da ein Takt von 1024 Hz für die RTC eingestellt wurde, dauert es genau eine Sekunde bis die RTC bis 1023 hoch gezählt hat. Der Prescaler für den Takt wird anschließend auf 1 gesetzt:

Um dafür zu sorgen das beide Taktquellen (RTC-Takt und Systemtakt) synchron laufen, wird das SYNCBUSY-Bit im Statusregister abgefragt und solange dieses Bit nicht auf High steht, sprich beide Taktquellen sind synchron, läuft das Programm nicht weiter:

Nun muss noch der Interruptlevel und der Auslösegrund des Interrupts festgelegt werden. Diesen wird auf Low gesetzt. Als Quelle soll der Overflow Interrupt genutzt werden.

Jetzt müssen noch die Interrupts aktiviert werden. Dazu wird einmal das Global Interrupt Enable-Bit gesetzt, sowie Interrupts mit der Priorität Low im Interrupcontroller freigeschaltet.

Nun löst die RTC jede Sekunde einen Overflow Interrupt aus und springt in die entsprechende ISR. Diese kann wie folgt genutzt werden.

In der ISR kann z. B. eine Variable hochgezählt werden um damit eine Uhr zu realisieren. Auch sind mit der RTC sehr einfache Zeitmessungen für größere Zeiträume problemlos möglich. So muss keiner der kostbaren Timer für
z. B. eine 5 Sekunden Pause genutzt werden. Durch die Möglichkeit eines Compare Match Interrupts kann die RTC auch nach einer bestimmten Zeit einen Interrupt auslösen (z. B. alle 0,7 Sekunden).

Das komplette Projekt ist in meinem GitLab-Repository zu finden.

Last Updated on

2 Kommentare

  1. Um dafür zu sorgen das beide Taktquellen (RTC Takt und Systemtakt) synchron laufen, wird das “SYNCBUSY” Bit im Statusregister abgefragt und solange dieses Bit nicht auf High steht, sprich beide Taktquellen sind synchron, läuft das Programm nicht weiter:
    while(RTC.STATUS & RTC_SYNCBUSY_bm);?
    or while(!(OSC.STATUS & RTC_SYNCBUSY_bm)); ?

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.