Einen schönen guten Abend,
ich programmiere gerade ein Programm, bei dem es notwendig wird, 2 8 Bit
Timer zu benutzen. Nur leider wird der Timer 0 immer ignoriert, wenn
Timer 2 im Programm implementiert ist. Sobald ich die
Initialisierungszeilen von einem der beiden Timer auskommentiere,
fünktioniert der jeweilige Timer einwandfrei. Nur zusammen funktionieren
sie nicht. Mir scheint so, als wenn Timer2 eine höhere Priorität als
Timer0 aufweist oder dessen Overflow irgendwie überschreibt. Jedenfalls
löst Timer0 nie einen Overflow aus, wenn Timer 2 mit im Programm ist.
Woran kann das liegen? Hab im Forum schon überall gesucht, aber nichts
gefunden.
Der Quellcode liegt im Anhang.
Vielen Danke!
TIMSK = 1;
TIMSK = 64;
Abgesehen von den "magic numbers" - überleg doch mal genau, was diese
Instruktionen bewirken.
Nicht stur reinschreiben, sondern mit oder/und arbeiten.
TIMSK = 1 bewirkt, dass der Timer0 Overflow aktiviert wird und TIMSK =
64 das Gleiche beim Timer2 Overflow. Was ist denn daran nicht richtig?
Ich benutze auch WinAVR als Compiler und AVR-Studio zum Programmieren,
aber bei mir kommt lediglich eine Warnung: „control reaches end of
non-void function“. Das dürfte eigentlich nicht das Problem sein.
@crazy horse, jetzt weis ich, was du meinst. Hups, mir ging grad ein
Licht auf. Statt 1 und 64 TIMSK = 65 hinschreiben. Manchmal kommt man
auch echt nicht auf die einfachsten Sachen. Jetzt funktionierts!
Vielen Dank nochmal!
Grüße Thomas
Thomas wrote:
> TIMSK = 1 bewirkt, dass der Timer0 Overflow aktiviert wird und TIMSK => 64 das Gleiche beim Timer2 Overflow. Was ist denn daran nicht richtig?
Jein.
TIMSK = 1 bewirkt, dass ausschliesslich_ der _Timer0 Overflow
aktiviert wird.
TIMSK = 64 bewirkt, dass ausschliesslich_ der _Timer2 Overflow
aktiviert wird.
Was du brauchst, ist TIMSK = 65 oder besser:
TIMSK = (1<<TOIE2)|(1<<TOIE0);
Gruß,
Magnetus
Ja ganz genau. Frag mich, warum ich darauf nicht selbst gekommen bin.
Aber nochmal eine Fragen, was ist an "TIMSK = (1<<TOIE2)|(1<<TOIE0);"
besser, als an der einfachen Schreibweise?
Vielen Dank!
Grüße Thomas
> Aber nochmal eine Fragen, was ist an "TIMSK = (1<<TOIE2)|(1<<TOIE0);"> besser, als an der einfachen Schreibweise?
Weil es unmissverständlich ist.
Wenn ich "TIMSK = 65;" schreibe, weiss ich zwar, dass das Register mit
dem Wert 65 beschrieben wird, aber es ist nicht klar, was das bewirkt.
Wenn ich "TIMSK = (1<<TOIE2)|(1<<TOIE0);" schreibe, weiss ich dass die
Bits "TOIE2" und "TOIE0" gesetzt (und die restlichen gelöscht) werden.
Gruß,
Magnetus
ausserdem funktioniert das dann auch garantiert bei einem anderen AVR,
obwohl dort evtl. die Bits an einer anderen Stelle sitzen. Dann sitz du
mit deinen 65 auf dem Schlauch. Zu einem anderen AVR gibts ne neue
.def-Datei, und schon passt der Kram wieder.
Für mich ist aber auch der Hauptgrund die bessere Lesbarkeit.
Gut, überzeugt. Ich werd es abändern, zumal die Sache mit dem Anderen
AVR schon wichtig ist, da ich den Mega16 nur zum Testen nehme. In der
Schaltung, die ich dazu erstellt hab, nehm ich nur den Mega8, der für
diese Anwendung völlig ausreicht.
Vielleicht noch kurz zur Erläuterung: Den Timer2 brauch ich zum Zählen
der Schleife im Unterprogramm (7-Segment Multiplexer) und den Timer0 zum
Abtasten eines Drehimpulsgebers. Muss ich aber alles noch programmieren.
Mit Hilfe des Drehimpulsgebers wird dann die Zahl erhöht/verringert. Das
ganze soll nach Möglichkeit so geschehen, dass bei langsamen Drehen die
Werte um jeweis eine Stelle erhöht werden und beim schnellen Drehen des
Drehimpulsgebers mehrere Schritte auf einmal gemacht werden.
Grüße Thomas