Forum: Mikrocontroller und Digitale Elektronik Timer zu langsam?


von idler (Gast)


Lesenswert?

Hallo allerseits:

Ich habe folgendes Problem:

Ich habe einen 8 bit Timer, der wie folgt koniguriert ist,

  TIMSK0 |= (1<<1);
  TCCR0A = (1<<1) | (0<<0);
  TCCR0B = (1<<1) | (1<<0);
  OCR0A = 1;

also alle 8 us einen Interrupt auslöst. (Prozessor ATmega324p oder 
ATmega168 hat eine Taktrate von 8 MHz)

In der ISR hab ich nichts weiter als:

  PORTB ^= (1 << 3);

Die Frequenz die ich mit dem Oszi messe, ist jedoch nur halb so groß wie 
ich sie haben will. (Die eins an B3 bleibt 16 us)

Eigentlich will ich ja sogar einen Prescaler von 8 verwenden und OCR0A 
auf 5 setzen, dann messe ich jedoch anstatt 5 us ganze 6,5 us.

Woran könnte das liegen?
Danke im Vorraus.

von Karl H. (kbuchegg)


Lesenswert?

Wenn du denkst, dass ich mir jetzt das Datenblatt hole, um zu sehen was 
du da eigentlich konfiguriert hast, hast du dich geschnitten.

von doc (Gast)


Lesenswert?

also 8us sind schon verdammt knapp. das sind ja nur 64 takte (bei 8 
mhz). da verbingt der us sowieso die meiste zeit im interrupt - ich 
vermute mal, das wird (so) nix.
einer der fälle, wo eine normale warteschleife ohne timer (-> mit 
AUSGESCHALTETEN interrupts) besser ist :-)

von Hc Z. (mizch)


Lesenswert?

Zum Einen ist etwas wie
1
TCCR0B = (1<<1) | (1<<0);
wenig aufschlussreich.  Da gehört etwas wie
1
TCCR0B = (1<<CS01)
hin, um das benötigte Minimum an Informationen mitzuliefern.

Dasselbe gilt für TCCR0B, wo Du es dem Leser überlässt, herauszufieseln, 
dass Du vermutlich WGM01 setzst und somit CTC Mode vorliegt.  Denke 
daran, dass meist Du selbst der Leser bist, z.B. in 2 Monaten, wo Du den 
Modus nicht mehr im Kopf hast, und somit Dich selbst nervst mit so 
schluderiger Darstellung.

Aaaaalso, wir haben CTC Mode.  Für den sagt das Datenblatt:
1
Focx = Fclkio / (2 * N * (1 + OCRx))

Siehst Du das '1 +'?  Somit teilst Du zusätzlich durch zwei und bekommst 
das, was Du gemssen hast.

von Michael (Gast)


Lesenswert?

Hallo.
Das ist alles korrekt, so wie es ist. Zur Erklärung:
- Du läßt Timer0 im CTC-mode laufen (TCCR0A = (1<<1) | (0<<0))
  Das bedeutet, der Timer läuft von 0 bis zum Wert von OCR0A.
- Du hast für den Clock des Timer0 den IOClock/64 gewählt
  (TCCR0B = (1<<1) | (1<<0))
  Das bedeutet bei 8MHz: Timer0-Takt ist 64*(1/8MHz)= 8us.

Da OCR0A=1 ist, vergehen 2 TimerTakte bis zum Interrupt. Also alle 16us.

von idler (Gast)


Lesenswert?

Sorry wegen der schlampigen Angaben.
@ Hazeh Zimmerer: thx, das isses wohl.

Also war CTC-Mode.

IN TCCR0A hab ich WGM01 gesetzt --> CTC Mode
In TCCR0B den Prescaler auf 64 gesetzt
In TIMSK0 Compareregister A ausgewählt.

Wie könnte ich denn noch alle 5 us eine globale Variable inkrementieren 
und gleichzeitig  eine globale Variable auf einen immergleichen wert 
setzen?

@doc, wie meinst du das ohne Timer?

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
Noch kein Account? Hier anmelden.