Hallo! ich versuche gerade den Watchdog für einen Software-Reset in meiner Applikation auszuprobieren. Dazu habe ich wdt_enable(WDTO_2S); in meine Applikation eingebaut. den wdt_reset(); in meiner while(1) schleife habe ich auskommentiert, um dem watchdog zuzusehen. Nach ziemlich exakt 2 Sekunden wird der AVR resettet. Nur anstatt das Programm von vorne auszuführen schreibt er mir nur noch kryptische Zeichen auf meine rs232 schnittstelle und lässt auch nichtmal die erste LED leuchten... Läuft also garnicht richtig... Selbst ein neues programmieren löst das Problem nicht! Flash programming und verify läuft wunderbar aus avr studio (ISP). Nur sobald das beendet ist kommen wieder die kryptischen Zeichen. Erst ein Strom weg + Strom da löst das Problem! Habe nun schonmal versucht direkt am Anfang meiner Applikation ein "wdt_disable()" einzufügen. Keine Änderung. Was kann das sein? Vielen Dank!
> Habe nun schonmal versucht direkt am Anfang meiner Applikation ein > "wdt_disable()" einzufügen. Keine Änderung. Der läßt sich nicht so einfach deaktivieren. Wobei in C bin ich mir da nicht so sicher. Aber ich denke das beim Watchdog reset nicht alle Register bzw. Variablen so initialisiert werden wie beim Power On Reset. z.B. werden einige Register Bits gelöscht wenn man eine 1 reinschreibt. Also : RegisterX=0b00001000 Setzt beim Power On Reset Bit Nummer 3 weil vorher eine 0 drinnestand ABER : Jetzt kommt der Watchdog Reset und bit Nummer 3 ist schon gesetzt RegisterX=0b00001000 würde dann zu einem Löschen von Bit 3 führen.
Ohne vollständiges Listing können alle außer Dir die Ursache nur raten. Wenn Du ganz lieb zu uns sein willst, tust Du auch noch einen Schaltplan dabei. Edit: Ach ja, und die Fuses.
wie in dem oben verlinkten thread beschrieben, scheint bei mir ebenfalls das Problem aufzutreten, dass der AVR garnicht schnell genug den watchdog abschalten kann nach einem watchdog reset. Der Watchdog reset scheint zu bewirken, dass der watchdog auf die kürzestmögliche Zeit gestellt wird. Folgender code behebt das Problem:
1 | //----------------------------------------------------------------------------
|
2 | // wdt_init - Watchdog Init used to disable the CPU watchdog
|
3 | // placed in Startcode, no call needed
|
4 | #include <avr/wdt.h> |
5 | |
6 | void wdt_init(void) __attribute__((naked)) __attribute__((section(".init1"))); |
7 | void wdt_init(void) |
8 | {
|
9 | MCUSR = 0; |
10 | wdt_disable(); |
11 | |
12 | return; |
13 | }
|
Allerdings wird hierbei bereits das MCUSR Register resettet! Wenn ich das weglasse resettet der avr sich ebenfalls zu schnell und alles spinnt. Nur mit exakt diesem code Funktioniert die Applikation auch mit wd reset. Gibt es eine Möglichkeit in so einer .init section das mcusr register vor dem Löschen zu sichern?
1 | uint8_t mcusr_mirror __attribute__ ((section (".noinit"))); |
2 | |
3 | void get_mcusr(void) __attribute__((naked)) _attribute__((section(".init1"))); |
4 | void get_mcusr(void) |
5 | {
|
6 | mcusr_mirror = MCUSR; |
7 | |
8 | // disable the dog
|
9 | MCUSR = 0; |
10 | wdt_disable(); |
11 | }
|
Miles schrieb: > Allerdings wird hierbei bereits das MCUSR Register resettet! Welchen Sinn soll das haben, das Register überhaupt zu löschen? mfg.
Was spricht dagegen, das MCUSR erst in eine Variable zu sichern? Thomas Eckmann schrieb: > Welchen Sinn soll das haben, das Register überhaupt zu löschen? Weil sonst der Watchdog permanent die Anwendung resettet.
Fred schrieb: > Weil sonst der Watchdog permanent die Anwendung resettet. Dazu reicht es aber, nur das WDRF-Flag zu löschen. mfg.
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.