Ich habe eine Problem mit dem Timer, und zwar möchte ich eine Frequenz erzeugen, die verändert werden kann, ohne dass beim Wechseln der Frequenz Glitches auftreten. Genau das ist im CTC Modus aber der Fall: Habe ich am Anfang z.B. den Wert 128 im Compare Register stehen, und schreibe danach den Wert 64 rein, dann kann es passieren, dass der 16bit-Timer bis 65535 zählt, wenn der Zählerstand beim Reinschreiben irgendwo zwischen 64 und 128 war, da der Compare dann verpasst wird. Gibt es dazu ein Workaround ?
Ja. Zum richtigen Zeitpunkt reinschreiben. Ist die Zeit lang genug, dann per Match-Interrupt. Wenn nicht, pollen.
Das hatte ich mir schon gedacht: Es gibt also keine ordentliche Lösung. Das mit dem Interrupt ist nicht so einfach, da noch andere Interrupts eingeschaltet sind. Und die verzögern dann den Compare Interrupt, was das Problem also nicht löst. Pollen ist daher die einzigste Lösung. Also inline Assembler bzw eine Assembler Funktion, da der dumme Compiler die Berechnung der Werte für die Register zwischen die Timer Abfrage und die Ausgabe der neuen Werte packt...
Wie schnell läuft Dein Timer denn und wie klein können Deine Compare-Werte werden? Wenn alle anderen Interrupt-Handler ausreichend kurz sind, dann sollte das bei nicht zu hohen Frequenzen eigentlich keine Probleme geben.
Die Frequenzen liegen bei 10kHz bis 250kHz. Das bedeutet also 500kHz Interruptfrequenz...
Ich hab bissher immer den Timer angehalten und OCR und TCNT entsprechend neu gesetzt. Alternative soll sowas laut DB auch über Fast PWM Modus gehen, habs aber noch nicht ausprobiert.
Stimmt, aber leider brauche ich beide OCR Register, da ich 2 Signale erzeugen muss, die gegenphasig sind. Da muss ich wohl auf einen der tinys wechseln, bei denen OCR1A-C doppelt gepuffert sind.
Hi, wie wäre es, den Timer beim Einstellen des neuen Compare Matches einfach zurückzusetzen? Für kleine Compare Matches ergibt sich dann eine bessere Ausgabe und der Timer/Counter läuft nicht mehr bis Ultimo durch. Bei größeren Werten der Compare Matches haste dann aber wieder Glitch... Gruß Fred
Pollen hilft da auch nichts, wenn noch andere Interrupts laufen. Dann dauert der Polling-Zyklus auch nicht immer gleich lang. Wie siehts denn damit aus, in den Interrupts nur Infos zu sammeln und die dann im Hauptprogramm zu bearbeiten? Ciao Willi Wacker
hallo, "...da ich 2 Signale erzeugen muss, die gegenphasig sind." inverter benutzen ?
Ein unausgegorener Denkansatz: Der Problemfall liegt ja nur dann vor, wenn der OCR Wert kleiner werden soll. Dann müsste man sich aber ausrechnen können, worauf der Timer gesetzt werden muss, damit er (samt einem Überlauf) bei Erreichen des neuen OCR Wertes noch genügeng Zählpulse für den vorhergehenden OCR Wert tickt. Alles klar? (Das da oben klingt grässlich) Ein Beispiel: Dein Timer soll der Einfachheit halber bis 16 zählen, dann erfolgt ein Überlauf. Der OCR sei 10 Jetzt willst du einen neuen OCR von 7 Der Timer sei momentan bei 8 (müsste also bei einem OCR von 10 noch 2 mal ticken). D.h. wenn ich den OCR auf 7 setzte und den Timer auf 5, dann kriege ich noch 2 Ticks bis der CTC das nächste mal zuschlägt. d.h. im jetzigen Durchagng macht der Timer immer noch insgesammt 10 Ticks (8 als der OCR noch auf 10 war und 2 als der OCR schon auf 7 umgestellt war) und im nächsten Durchgang macht er dann die gewünschten 7 Ticks. Der OCR sei wieder auf 10 und wieder willst du ihn auf 7 setzen. Aber diesmal sei der Timerwert erst 1. d.h. der Timer muss noch 9 Ticks machen. d.h. du musst den Timer auf 7 - 9 + 16 = 14 vorbelegen.
Karl heinz Buchegger wrote: > Ein unausgegorener Denkansatz: > Der OCR sei wieder auf 10 und wieder willst du ihn auf 7 > setzen. Aber diesmal sei der Timerwert erst 1. > d.h. der Timer muss noch 9 Ticks machen. d.h. du musst > den Timer auf 7 - 9 + 16 = 14 vorbelegen. Das ist Unsinn, wenn der jetzige Timerwert kleiner als der neue OCR Wert ist, gibt es ja auch kein Problem.
Willi Wacker wrote: > Wie siehts denn damit aus, in den Interrupts nur Infos zu sammeln und > die dann im Hauptprogramm zu bearbeiten? Meinst du die anderen Interrupts die noch an sind ? Wie bereits geschrieben: Der Timer erzeugt 250kHz. Selbst bei 16MHz sind das nur max 64 Takte, die schnell weg sind, alleine durch das pushen und popen von den Registern in der Interruptroutine. Selbst die doppelt gepufferten OCR Register bringen nichts: Was passiert, wenn der Compare genau zwischen den Änderungen der OCR1A und OCR1C Register passiert ? -> Glitch. Ich denke es gibt nur eine Lösung: Alle Werte berechnen cli warten bis Timer Compare OCR1A=ocr1a_wert OCR1C=ocr1c_wert sei
im PWM Modus wird die Pufferung des Compareregisters eingeschaltet lt. Datenblatt des ATMEGA 32. In den anderen Modi ist er abgeschaltet. mfg Quehl
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.