Hallo zusammen,
ich steh irgendwie aufm Schlauch und komm nicht weiter, vielleicht hat
einer von euch ne Idee.
Ich hab nen Bootloader auf nem ATMEGA328P ab 0x7000 (byte adresse),
dieser wird nach einem Power-On Reset auch korrekt angesprungen, meldet
sich und funktioniert soweit.
Ins Hauptprogramm springe ich dann via
void (*start)( void ) = 0x0000;
Auch das Hauptprogramm startet und arbeitet einwandfrei.
Aaaber ich komme leider nicht wieder zurück in den Bootloader per
Software, noch nicht einmal via Hardware-Reset-Taster. Beide Varianten
haben denselben Effekt.
Hardware: Reset Pin low ziehen
Software: cli(); wdt_enable(WDTO_15MS); while (1);
Der Bootloader startet erneut aber scheint sich dann periodisch alle
paar ms zu resetten so als ob der Watchdog zuschlägt. Ich habe aber
sowohl im Bootloader als auch im Anwendungsprogramm den Befehl
wdt_disable(); direkt am Anfang. Im Anwendungsprogramm funktioniert das
auch, d.h. wenn ich ohne Bootloader zu flashen den watchdog reset
ausführe startet das Anwendungsprogramm neu und läuft einwandfrei.
Direkt die Bootloaderadresse anspringen klappt leider auch nicht:
void (*bootloader)( void ) = (void*)0x7000;
bootloader();
Da geht dan gar nix.
Ohne Bootloader läuft der PC offenbar wie erwartet hoch bis zum Überlauf
und das Hauptprogramm startet korrekt.
Jemand ne Idee?
Vielen Dank für eure Hilfe :)
p.s. word adresse void (*bootloader)( void ) = (void*)0x3800; hab ich
auch versucht, leider ebenfalls ohne Erfolg. Was wäre eigentlich
theoretisch richtig?
Wie sehen die Fuse-Bits aus? Stimmen denn die Einstellungen für den
Bootloader?
Außerdem wäre etwas Code ganz nützlich, um Softwarefehler
auszuschließen.
Grüße Oliver
So, habe nun doch noch mal ein extra Testprogramm ebenfalls nach Vorlage
geschrieben.
Folgendes Verhalten:
- Sprung nach 0x3800 funktioniert hier, ich gehe davon aus das bei
meiner eigenen ASW irgendwelche Interrupts bzw. Peripherie die noch
läuft das Problem darstellen bzw. in der Folge die umgebogene
Interruptvectortabelle. Muss ich aber noch untersuchen.
- Der WDT-Reset funktioniert aber nach wie vor NICHT. Selbes Verhalten
wie bei meiner ASW: Auf dem Terminal läuft ununterbrochen
...
Hallo hier ist deHallo hier ist deHallo hier ist deHallo hier ist
deHallo hier
ist deHallo hier ist deHallo hier ist deHallo hier ist deHallo hier ist
deHallo
hier ist deHallo hier ist deHallo hier ist deHallo hier ist deHallo hier
ist deH
allo hier ist deHallo hier ist deHallo hier ist deHallo hier ist deHallo
hier is
t deHallo hier ist deHallo hier ist deHallo hier ist deHallo hier ist
...
Testprogramm:
#include <avr/io.h>
#include <avr/wdt.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>
#include <util/delay.h>
#include "uart.h"
#define UART_BAUD_RATE 9600
int main()
{
unsigned int c;
void (*bootloader)( void ) = (void*)0x3800; // Achtung Falle: Hier
Word-Adresse
uart_init( UART_BAUD_SELECT(UART_BAUD_RATE,F_CPU) );
sei();
uart_puts_P("\n\rHier ist das Anwendungsprogramm...");
for(;;)
{
c = uart_getc();
if(!(c & UART_NO_DATA))
{
switch( (unsigned char)c)
{
case 'b':
uart_puts("\n\rSpringe zum Bootloader...");
_delay_ms(1000);
bootloader();
break;
case 'r':
uart_puts("\n\rReset...");
_delay_ms(1000);
cli(); // Interrupts global abschalten
wdt_enable(WDTO_15MS); // Watchdog aufziehen auf 15ms
while (1); // warten, bis er zubeisst...
break;
default:
uart_puts("\n\rDu hast folgendes Zeichen gesendet: ");
uart_putc((unsigned char)c);
break;
}
}
}
return 0;
}
Für Hinweise was das Problem beim Watchdog Reset sein könnte wäre ich
dankbar, da ich eigentlich dachte hierbei wird der Controller komplett
reinitialisiert, aber irgendas muss gegenüber Power-On ja offenbar
anders sein...
Schönes WE euch allen :)
falls jemand über dieselbe Falle stolpert:
Lösung für das Watchdog Problem:
MCUSR = 0; // Sonst funktioniert das Abschalten des Watchdogs nicht
wdt_disable();
Es würde auch reichen nur das Watchdog-Bit in MCUSR zu löschen aber ich
brauch den Rest nicht. Schade das wdt_disable(); sich nicht darum
kümmert, das habe ich fälschlicherweise vorausgesetzt.
(siehe auch Beitrag "AVR spinnt nach Watchdog reset!")
Janus schrieb:> falls jemand über dieselbe Falle stolpert:>> Lösung für das Watchdog Problem:> MCUSR = 0; // Sonst funktioniert das Abschalten des Watchdogs nicht> wdt_disable();
Das Problem hatte ich auch schon. Eigentlich macht es aber gar keinen
Sinn, dass MCUSR gelöscht werden muss?
Das ist bestimmt Absicht, damit der Watchdog nicht aus versehen bei
einem Absturz deaktiviert wird. Bei vielen AVR kann man ihn gar nicht
abschalten, nur einschalten.
Der Reset initialisiert fast alles, den Watchdog ausnahmsweise nicht.
Wenn er an ist, bleibt er an.
Stefan us schrieb:> Das ist bestimmt Absicht, damit der Watchdog nicht aus versehen bei> einem Absturz deaktiviert wird.
Das ist Absicht. Wenn man schon etwas sicherheitsrelevantes per
Software abschalten kann, dann aber auch nicht "mal eben".
Da ich in C und nicht in Assembler programmiere weiß ich es jetzt nicht
ganz genau, aber zum Beschreiben des EEPROM muss wohl auch eine
spezielle Sequenz eingehalten werden.
Stefan us schrieb:> Das ist bestimmt Absicht, damit der Watchdog nicht aus versehen bei> einem Absturz deaktiviert wird. Bei vielen AVR kann man ihn gar nichtMartin Kreiner schrieb:> Das ist Absicht. Wenn man schon etwas sicherheitsrelevantes per> Software abschalten kann, dann aber auch nicht "mal eben".
Das Handbuch ist da nicht ganz eindeutig. Um Attiny85 Handbuch wird auf
Seite 42 nicht erwähnt, dass zum Abschalten MCUSR beschrieben werden
muss. wdt_disable() scheint nur die Zugriffe auf WDCE und WDE
abzubilden.
Im Beispielcode ist der Zugriff auf MCUSR aber ohne weitere Erklärung
enthalten.
Tim schrieb:> Das Handbuch ist da nicht ganz eindeutig. Um Attiny85 Handbuch wird auf> Seite 42 nicht erwähnt, dass zum Abschalten MCUSR beschrieben werden> muss.
In der Beschreibung des WDE Bits steht es explizit drin.
Stefan Ernst schrieb:> Tim schrieb:>> Das Handbuch ist da nicht ganz eindeutig. Um Attiny85 Handbuch wird auf>> Seite 42 nicht erwähnt, dass zum Abschalten MCUSR beschrieben werden>> muss.>> In der Beschreibung des WDE Bits steht es explizit drin.
Stimmt, dann hat Atmel es in der Beschreibung auf Seite 42 vergessen.
Sollte man mal dem Support melden...