Hallo,
wenn man im Net nach "Watchdog" sucht, findet man einen Beitrag, der offensichtlich so nicht ganz korrekt ist.
Nachdem ich mir die Mühe gemacht hatte, ihn um die deutsche Übersetzung zu ergänzen, mußte ich im Praxistest feststellen, daß er leider unvollständig bzw. teilweise sogar nicht ganz richtig ist.
Daher hier einige grundsätzliche Fakten, die am besten auch auf Seiten 48ff im Manual vom
verwendeten ATMega8515 nachzuschlagen sind.
http://www.atmel.com/dyn/resources/prod_documents/2512S.pdf
Eine allgemeine Einrichtung des Wachhundes kann durch unten angegebenen Code erzielt werden.
Wichtig: Die Interruptfreigabe muß disabled werden mit dem ASM-Befehl CLI.
Am Ende des Strings den Wachhund "an die Leine nehmen" mit dem Resetbefehl
WDR (Watchdog Reset) und dann mit ASM-Befehl SEI die globale Interruptfreigabe ermöglichen.
Der Watchdog ist im Prinzip ein autonomer Timer, der selbständig einen Reset durchführt, wird der Timer nicht im Programmverlauf in regelmäßigen Abständen auf Null gesetzt.
Dauert die Ausführung eines Programmabschnitts also zu lange zwischen den Nachlademarken (Null-Ladewerten - Watchdog Reset - ASM-Anweisung "WDR" ( nicht Südwestfunk, nein, nicht Radio Bremen)-) für den Watchdog, wird davon ausgegangen, daß der Prozessor dort "hängengeblieben" ist und nach einem Programmneustart verlangt.
Im MC ist dazu ein eigener 1-MHz-Taktgenerator, der unabhängig von der MCU-Taktfrequenz läuft.
Ist der im Prescaler voreingestellte Wert der Zeit, zu der ein Reset ausgeführt werden soll, erreicht bzw. überschritten, wird ein Impuls mit einer Taktfrequenzlänge generiert, welcher wiederum einen Resetimpuls von definierter Länge zum Reset des MC triggert. So wird dann der "Systemreset" nach "Watchdog-Manier" ausgeführt. Die verschiedenen Resetereignisse werden noch durch Setzten von bestimmten Bits im Status- und Controlregister differenziert und protokolliert.
Der Watchdog kann also, ist er nicht richtig eingerichtet, durchaus mehr schaden als nutzen, indem er dann das gesamte Programm durch Reset zum Absturz bringt. (Reset=> in der Regel Sprung an Codeanfang, Löschung der Registerinhalte, etc.)
Um ein unbeabsichtigtes "Anschlagen" des "Wachhundes" zu vermeiden, sollte im Verlaufe des Programms, insbesondere vor Zeitschleifen oder seriellen Datentransfer-Operationen dieser
Timer selbst außer Kraft gesetzt werden mit Reset des Timers, und dazu die "WDR"-Anweisungen reingeschrieben werden.
Positiv wirkt sich der Watchdog aber dann aus,
wenn "Peripherie"-Geräte aus unerfindlichen Gründen
versagen und von Zeit zu Zeit neu initialisiert werden müssen, um das Gesamtprogramm wieder zur Funktion zu bewegen. Es wird dann auch die entsprechende Initialisierungsroutine am Anfang des Programms wieder durchlaufen.
(Übrigens andere Methode zur Inaktivierung des Watchdog im Programmverlauf: "Watchdog-disable" mit Ladewert 0b00010000 oder Hex 0x10 in Register WDTCR.) Wie hier:
Auch kann im Verlaufe eines Programms auf den Prescaler zugegriffen werden, hierbei ist allerdings zu beachten, daß diese Strings zeitkritisch sind. Es wird davon berichtet, daß diese
Anweisungen innerhalb von 4 bzw. 5 MCU-Takten unmittelbar aufeinander folgen müssen.
(Übrigens: Durch Setzen von Fuses können verschiedene Security-Level gewählt werden, die gerade diese Änderungen an den Watchdog-Einstellungen im Programmverlauf auch ihrerseits verhindern. Darauf beziehen sich auch die Modifikationen vom ATS90xx zum ATMegaxx.)
Zwingend notwendig ist der erste String im Codebeispiel mit "Watchdog enable", insbesondere dann, wenn er durch obigen "Disable-String" irgendwann mal komplett abgeschaltet war.
Also im Register WDTCR Bit 4 gesetzt, Bit 3 auch auf "Eins", also 0b00011000 bzw. Hex 0x18 .
Der Vorteiler (Prescaler) ist hier im Code-Beispiel durch Setzen von allen Bits WDP0 bis WDP2 im Register WDTCR auf den Maximalzeitwert von über 1 Sekunde eingestellt.
Zum Zugriff auf den Vorteiler muß nun noch das Bit 3 WDE gesetzt werden. Also String-Argument 0b00001111 bzw. Hex 0x0F,
wobei bei Einrichtung des Prescalers dieses ominöse Bit 4 von String "Watchdog-Enable" wieder auf "Null" stehen muß und nicht etwa auf "Eins".
Das scheint zunächst etwas unklar, und genau darauf bezieht sich die Fehlerquelle im eingangs erwähnten "Net"-Beitrag.
Oben im Codebeispiel ist's aber IMHO richtig, in der Reihenfolge korrekt angegeben und auch in der Praxis von mir getestet.
Übrigens wird - wie oben schon angeklungen - das Bit 3 im Control-und-Status-Register bei "Anschlagen" des "Wachhundes" gesetzt und kann dort auch ausgelesen werden, falls man das möchte (MCUCSR Bit WDRF).
Dieses "Watchdog-Reset-Flag" bleibt nach dem so gearteten Resetereignis erhalten, wird nur durch einen Power-On-Reset gelöscht.
Das ist beim Testlauf von Progs vielleicht eine ganz interessante Möglichkeit, evtl. Bugs aufzuspüren.
Gruß von Oskar01
wenn man im Net nach "Watchdog" sucht, findet man einen Beitrag, der offensichtlich so nicht ganz korrekt ist.
Nachdem ich mir die Mühe gemacht hatte, ihn um die deutsche Übersetzung zu ergänzen, mußte ich im Praxistest feststellen, daß er leider unvollständig bzw. teilweise sogar nicht ganz richtig ist.
Daher hier einige grundsätzliche Fakten, die am besten auch auf Seiten 48ff im Manual vom
verwendeten ATMega8515 nachzuschlagen sind.
http://www.atmel.com/dyn/resources/prod_documents/2512S.pdf
Eine allgemeine Einrichtung des Wachhundes kann durch unten angegebenen Code erzielt werden.
Wichtig: Die Interruptfreigabe muß disabled werden mit dem ASM-Befehl CLI.
Am Ende des Strings den Wachhund "an die Leine nehmen" mit dem Resetbefehl
WDR (Watchdog Reset) und dann mit ASM-Befehl SEI die globale Interruptfreigabe ermöglichen.
Code:
cli
ldi temp, 0x18 ;Watchdog enable
out WDTCR, temp
ldi temp, 0x0F ;Prescaler Set
out WDTCR, temp
wdr
sei
rjmp start
Der Watchdog ist im Prinzip ein autonomer Timer, der selbständig einen Reset durchführt, wird der Timer nicht im Programmverlauf in regelmäßigen Abständen auf Null gesetzt.
Dauert die Ausführung eines Programmabschnitts also zu lange zwischen den Nachlademarken (Null-Ladewerten - Watchdog Reset - ASM-Anweisung "WDR" ( nicht Südwestfunk, nein, nicht Radio Bremen)-) für den Watchdog, wird davon ausgegangen, daß der Prozessor dort "hängengeblieben" ist und nach einem Programmneustart verlangt.
Im MC ist dazu ein eigener 1-MHz-Taktgenerator, der unabhängig von der MCU-Taktfrequenz läuft.
Ist der im Prescaler voreingestellte Wert der Zeit, zu der ein Reset ausgeführt werden soll, erreicht bzw. überschritten, wird ein Impuls mit einer Taktfrequenzlänge generiert, welcher wiederum einen Resetimpuls von definierter Länge zum Reset des MC triggert. So wird dann der "Systemreset" nach "Watchdog-Manier" ausgeführt. Die verschiedenen Resetereignisse werden noch durch Setzten von bestimmten Bits im Status- und Controlregister differenziert und protokolliert.
Der Watchdog kann also, ist er nicht richtig eingerichtet, durchaus mehr schaden als nutzen, indem er dann das gesamte Programm durch Reset zum Absturz bringt. (Reset=> in der Regel Sprung an Codeanfang, Löschung der Registerinhalte, etc.)
Um ein unbeabsichtigtes "Anschlagen" des "Wachhundes" zu vermeiden, sollte im Verlaufe des Programms, insbesondere vor Zeitschleifen oder seriellen Datentransfer-Operationen dieser
Timer selbst außer Kraft gesetzt werden mit Reset des Timers, und dazu die "WDR"-Anweisungen reingeschrieben werden.
Positiv wirkt sich der Watchdog aber dann aus,
wenn "Peripherie"-Geräte aus unerfindlichen Gründen
versagen und von Zeit zu Zeit neu initialisiert werden müssen, um das Gesamtprogramm wieder zur Funktion zu bewegen. Es wird dann auch die entsprechende Initialisierungsroutine am Anfang des Programms wieder durchlaufen.
(Übrigens andere Methode zur Inaktivierung des Watchdog im Programmverlauf: "Watchdog-disable" mit Ladewert 0b00010000 oder Hex 0x10 in Register WDTCR.) Wie hier:
Code:
ldi temp, 0x10 ;Watchdog disable
out WDTCR, temp
Auch kann im Verlaufe eines Programms auf den Prescaler zugegriffen werden, hierbei ist allerdings zu beachten, daß diese Strings zeitkritisch sind. Es wird davon berichtet, daß diese
Anweisungen innerhalb von 4 bzw. 5 MCU-Takten unmittelbar aufeinander folgen müssen.
(Übrigens: Durch Setzen von Fuses können verschiedene Security-Level gewählt werden, die gerade diese Änderungen an den Watchdog-Einstellungen im Programmverlauf auch ihrerseits verhindern. Darauf beziehen sich auch die Modifikationen vom ATS90xx zum ATMegaxx.)
Zwingend notwendig ist der erste String im Codebeispiel mit "Watchdog enable", insbesondere dann, wenn er durch obigen "Disable-String" irgendwann mal komplett abgeschaltet war.
Also im Register WDTCR Bit 4 gesetzt, Bit 3 auch auf "Eins", also 0b00011000 bzw. Hex 0x18 .
Code:
ldi temp, 0x18 ;Watchdog enable
out WDTCR, temp
Der Vorteiler (Prescaler) ist hier im Code-Beispiel durch Setzen von allen Bits WDP0 bis WDP2 im Register WDTCR auf den Maximalzeitwert von über 1 Sekunde eingestellt.
Zum Zugriff auf den Vorteiler muß nun noch das Bit 3 WDE gesetzt werden. Also String-Argument 0b00001111 bzw. Hex 0x0F,
wobei bei Einrichtung des Prescalers dieses ominöse Bit 4 von String "Watchdog-Enable" wieder auf "Null" stehen muß und nicht etwa auf "Eins".
Das scheint zunächst etwas unklar, und genau darauf bezieht sich die Fehlerquelle im eingangs erwähnten "Net"-Beitrag.
Code:
ldi temp, 0x0F ;Prescaler Set
out WDTCR, temp
Oben im Codebeispiel ist's aber IMHO richtig, in der Reihenfolge korrekt angegeben und auch in der Praxis von mir getestet.
Übrigens wird - wie oben schon angeklungen - das Bit 3 im Control-und-Status-Register bei "Anschlagen" des "Wachhundes" gesetzt und kann dort auch ausgelesen werden, falls man das möchte (MCUCSR Bit WDRF).
Dieses "Watchdog-Reset-Flag" bleibt nach dem so gearteten Resetereignis erhalten, wird nur durch einen Power-On-Reset gelöscht.
Das ist beim Testlauf von Progs vielleicht eine ganz interessante Möglichkeit, evtl. Bugs aufzuspüren.
Gruß von Oskar01