Hallo Zusammen, ich bin am Verzweifeln. Meine Routine für TIMER0_OVF_vect wird nicht angesprungen. Warum keine Ahnung. Aus meiner Sicht sind alle IRs freigeschaltet und korrekt initialisiert. Könnte sich mal jemand den entsprechenden Code ansehen. Im Anhang der gesamte Code als ZIP-Archiv. Die Initialisierung befindet sich initTimer() im File main.c Danke für jeden Tipp. Gruß Frank
Das hier schaut komisch aus: TIMSK = 1<<TOIE0^1<<TOIE1^1<<TOIE2; Dachte man würde so schreiben: TIMSK = (1 << TOIE0) | (1 << TOIE1) | (1 << TOIE2) Schau doch mal im Disassembler, was da der Compiler so erzeugt. Aber ich schreib in Bascom, könnte hier also die Lizenz haben falsch zu liegen.
Hallo, ich habe gestern Abend noch ein wenig experimentiert. Das Ergebnis ist folgendes: Mit dieser Initialisierung ist die Anwendung letzte Woche noch gelaufen. Seit Montag nicht mehr. Auch wenn ich alle Änderungen die ich seit dem gemacht habe, zurücknehmen, wird der TIMER0_OVF_vect nicht angesprungen.
1 | void initTimer( void ) |
2 | {
|
3 | TCCR0 = 0; |
4 | TCCR0 = 1<<CS02; |
5 | |
6 | TCCR1A = 1<<CS10; |
7 | TCCR1B = 1<<CS10; |
8 | |
9 | TCCR2 = 0; |
10 | TCCR2 = 1<<CS11; |
11 | |
12 | TIMSK = 1<<TOIE0^1<<TOIE1^1<<TOIE2; // enable timer interrupt |
13 | }
|
Ändere ich die Parameter auf:
1 | void initTimer( void ) |
2 | {
|
3 | TCCR0 = 0; |
4 | TCCR0 = 1<<CS02; |
5 | |
6 | TCCR1A = 0; |
7 | TCCR1B = 1<<CS10; |
8 | |
9 | TCCR2 = 0; |
10 | TCCR2 = 1<<CS11; |
11 | |
12 | TIMSK = 1<<TOIE0^1<<TOIE1^1<<TOIE2; // enable timer interrupt |
13 | }
|
wird der TIMER0_OVF_vect angesprungen. Allerdings ist dann der Aufruf des Vektors für TIMER1_OFV_vect zu langsam und damit läuft meine gesamte PWM nicht mehr vernüftig. Genauso wird der Vektor angesprungen, wenn ich TOIE1 vollständig entferne. Für mich stellt sich jetzt die Frage, was genau ist falsch... Gruß Frank
> TCCR1A = 1<<CS10; > TCCR1B = 1<<CS10; Was das soll, weißt wohl sowieso nur Du selbst... Abgesehen davon: MWS hat im Prinzip Recht: EXOR (^) ist da unsinnig. Mach es mit OR (|) und klammere die Teilausdrücke (v.a. wegen der Übersicht).
Und noch ein kleiner Tip am Rande: Bei Funktionsprototypen ist extern flüssiger als Wasser...
Johannes M. wrote:
> Abgesehen davon: MWS hat im Prinzip Recht: EXOR (^) ist da unsinnig.
Ungewohnt, ja.
Aber da die Konstanten alle andere Werte haben, ist das auch nicht
unbedingt falsch. Das kann es also nicht sein.
TCCR0 = 0; TCCR0 = 1<<CS02; TCCR2 = 0; TCCR2 = 1<<CS11; Und da Du mit "=" arbeitest, kannst Du Dir das vorherige "=0" auch sparen.
Hallo, erstmal Danke für die Antworten. Ich habe das Konstrukt auch schon in der üblichen Schreibweise verwendet.
1 | void initTimer( void ) |
2 | {
|
3 | TCCR0 = 0; |
4 | TCCR0 = 1<<CS02; |
5 | |
6 | TCCR1A = 0; |
7 | TCCR1B = 1<<CS10; |
8 | |
9 | TCCR2 = 0; |
10 | TCCR2 = 1<<CS11; |
11 | |
12 | TIMSK = (1<<TOIE0)|(1<<TOIE1)|(1<<TOIE2); // enable timer interrupt |
13 | }
|
bringt keinen Unterschied! Fakt ist, setzte ich TCCR1A = 0 funktionierts! Setzte ich TCCR1A = 1<<CS10 laufen alle anderen Interuptaufrufe mit Ausnahme von TIMER0_OVF_vect korrekt und in der von mir erwarteten Geschwindigkeit. Setzte ich TCCR1A = 0 laufen alle Interupts nur Timer1 zu langsam. Da ich nicht wirklich der Krack in Mikrocontroller und C bin, bin ich mit meinem Latein am Ende. TCCR0 = 0 und TCCR2 = 0 sind mit Sicherheit überflüssige Angaben, da sie aber auch nicht wehtun, habe ich sie noch gelassen. Werden allerdings irgendwann wenn der Code sauber funktioniert entfernt. Wobei ich auch hier sehr merkwürde Effekte hatte. Die aber damit zusammen hängen können, dass irgendetwas anderes falsch ist. @Johannes Setzte ich TCCR1A und TCCR1B nicht funktioniert der Timer1 überhaupt nicht. Mir ist im Augenblick keine andere Alternative bekannt, den Timer1 korrekt zu initialisieren. Gruß Frank
Da niemand (außer dir) weiss welcher Prozessor, kann auch niemand prüfen in welchem Modus du den Timer betreibst, respektive warum es mit
1 | TCCR1A = 0; |
2 | TCCR1B = 1<<CS10; |
funtioniert, und mit
1 | TCCR1A = 1<<CS10; |
2 | TCCR1B = 1<<CS10; |
nicht. Abgesehe davon kann es nur in einem der beiden Register ein Bit mit dem Namen CS10 geben. Alles etwas Konfus. Werner
Werner B. wrote: > Abgesehe davon kann es nur in einem der beiden Register ein Bit mit dem > Namen CS10 geben. Das war das, was ich oben meinte...
Hi Werner, da hast Du verdammt Recht. Sorry, mein Controller ist ein ATMEGA8. Ich denke, ich habe den Fehler nach dem Studium der Unterlagen auch gefunden. CS10 für TCCR1A ist schlicht weg falsch. Hier ist TCCR1A = 0 korrekt. Zusätzlich setzte ich im TIMER0_OVF_vect den TCNT0 und nicht den TCNT1. Copy und Paste ohne nachdenken :-((, deshalb hat es letzte Woche auch noch alles korrekt funktioniert. Gruß Frank
1 | > TCCR1A = 1<<CS10; |
2 | > TCCR1B = 1<<CS10; |
3 | >
|
hallo was hier passiert kann ich dir sagen (hatte selber mal das problem) 1. variante
1 | > TCCR1A = 1<<0; |
2 | > TCCR1B = 1<<0; |
3 | >
|
2.variante
1 | > TCCR1A = 1<<WGM10; |
2 | > TCCR1B = 1<<CS10; |
3 | >
|
beide varianten sind gleichwertig mit deiner variante! wieso? die bitbezeichnung (CS10)steht für die bitnummer(0). wenn du CS10 woanders verwendest wird es als 0 interpretiert was aber jenach register eine andere funktion auslöst. mfg
Hallo Alex Alex, dank für die Zusammenfassung, ich hatte das als Abschluss für den Thread komplett vergessen zu schreiben. Gruß Frank
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.