mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Probleme mit Timer


Autor: Christof (Gast)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Ich will mit dem ATMEAG8535 eine Uhr realisieren.
Taktfrequenz = 8MHZ
Ich habe da jetzt Verständigungsprobleme mit dem 16Bit Timer1.

Kann mir jemand folgende Register genauer erklären?
TCCR1A=0x00;
TCCR1B=0x02;
TCNT1H=0x01;
TCNT1L=0xAA;
OCR1AH=0x00;
OCR1AL=0x00;
OCR1BH=0x00;
OCR1BL=0x00;

Mit welchen Werten muss ich die Register laden, damit alle 10ms oder
100ms der Timer1 ausgelöst wird?

Autor: Christof (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wenn mir jemand bei der Berechnung helfen könnte, wie ich auf 10ms bzw.
1ms komme!

Autor: ...HanneS... (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
"Kann mir jemand folgende Register genauer erklären?"

Ja, das Datenblatt... (ab Seite 107)

Wenn dich die vielen Hardware-Sonderfunktionen verunsichern, dann schau
dir doch erstmal die Standardfunktionen des Timers anhand des
Datenblatts eines Classic-AVRs an. Wenn du die verstanden hast,
verstehst du auch die (viel komplexeren) Timer der Megas.

Autor: Ingo Klöckl (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Servus,
TCCR1A/B sind die Steuerregister des Timers, die all die vielen
Funktionen ein- und ausschalten und konfigureren, da kommen wir gleich
dazu.
TCNT1H:L ist der eigentliche 16bit-Zählerinhalt, der je nach
Konfiguration hochzählt.
OCR1AH:L und OCR1BH:L sind Register, die zwei 16-bit-"Output
Compare"-Werte fassen.

Ich würd's so machen: Timer1 mit geeigneter Frequenz von Null
hochzählen lassen. Dazu wird die Systemfrequenz durch den Prescaler
heruntergeteilt. Bei einem bestimmten Wert (der als Output Compare-Wert
in OCR1AH:L geschrieben wird), wird ein Ouput Compare-Interrupt
ausgelöst und der Zähler automatisch (!) auf Null zurückgesetzt. Dann
zählt er wieder bis zum OCR1A-Wert und interruptet erneut und so fort.
Im Interrupt machst Du Deine Uhr-Inkrementiererei.

Also etwas konkreter (kein Datenblatt zur Hand, also mußt Du alle Bits
selber noch zusammensetzen :-) :
Timer 1 Prescaler auf 1024 setzen -> ergibt eine Zählfrequenz von 8
MHz/1024 = 7,8125 kHz. Du willst 100 Hz Interrupt-Frequenz -> alle 78
Zähltakte (7812.5/100=78) muß der Zähler einen OC-Interrupt auslösen
und zurückgestellt werden.

Also:
TCCR1A/B so einstellen: Prescaler=1024 (glaube Bits 0-2 in TCCR1A),
Modus=Output Compare mit CTC (Clear counter on match, das setzt Dir das
Zählerregister wieder auf Null, sobald der OCR1-Wert erreicht wurde -
automatisch, das ist der Modus 4, ist über die Bits WGMxx verstreut)
OCR1AL auf 78 setzen, OCR1AH auf 0 setzen.
TCNT1L und TCNT1H auf 0 setzen (Startwert ist null).

Das Verfahren hat den Vorteil, daß das Zählerladen einmal am Anfang
geschieht und Du nix mehr damit zu tun hast. Deine Registerbelegung aus
dem Posting geht über folgenden Weg:
TCCR1A definiert einen Prescaler von 8 (auswendig - stimmt vielleicht
nicht!) -> Zählfrequenz 8 MHz/8 = 1 MHz. D.h. jeder Zählertick dauert 1
us. Zähler wird mit $1AA=426 vorgeladen und erreicht nach
65536-426=65119 Takten seinen Max-Wert. Dann löst er den
Overflow-Interrupt aus, was somit alle 65 ms erfolgt. Da der TImer nun
den Wert 0 hat, muß er erneut mit dem Startwert vorgeladen werden
(warum in Deinem C-Programm dann nicht wieder $1CC sondern was größeres
steht?? muß das gleiche sein, sonst ist (nur der erste) Interrupt zu
spät dran).


Bei allen Verfahren muß man aber bedenken, daß der Systemtakt (die 8
MHz) sehr genau sein muß, sonst hast Du eine Pfusch-Uhr! D.h. die
Systemfrquenz darf nicht vom on-Chip-Oszillator kommen, sondern von
einem Quarz. Alternativ kann der 8535 einen Uhrquarz an TOSC1/2
betreiben. Dann hast Du am Timer2 eine Frequenz von genau 32,768 kHz
liegen, die Du eben anders herunterteilen mußt (analog, aber andere
Werte).

Grüße Ingo

Autor: Christof (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo!

Danke. Ich habe jetzt mal diese Einstellungen vorgenommen:
TCCR1A=0x00;
TCCR1B=0x05;
TCNT1H=0x00;
TCNT1L=0x00;
OCR1AH=0x00;
OCR1AL=0x78;
OCR1BH=0x00;
OCR1BL=0x00;

irgendwie klapt dies nicht?
Muss ich an den Registern OCR1BH und OCR1BL auch was einstellen?

Autor: Tobi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
""Kann mir jemand folgende Register genauer erklären?"

Ja, das Datenblatt... (ab Seite 107)"

immer noch...

Autor: ...HanneS... (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi...

Stell dir mal folgende Fragen:
- Welchen Interrupt willst du nutzen?
- Welche Parameter brauch der Timer dazu?
- Wozu dienen TCNT1(H/L)?
- Wozu dienen OCR1A(H/L)?
- Wozu dienen OCR1B(H/L)?

...HanneS...
(der der Sprache C nicht mächtig ist...)

Autor: Hubert.G (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich würde mal hier im Wiki , AVR-GCC-Tutorial unter Timer/Counter
nachlesen, ist in Deutsch und sehr gut verständlich

Autor: Christof (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ok ich habe mal auf der Wiki Seite alles nachgelesen.
Leider wird nicht von diesen Registern OCR1BH und OCR1BL erwähnt.
Ich will nur das z.b. der Timer 1 Überlauf alle 10ms ausgelöst wird.
(siehe Programm oben). Kann mir niemand mal ein Beispiel geben wie ich
diese Register einstellen muss?

TCCR1A=0x00; //das ist klar
TCCR1B=0x05; //das ist klar
TCNT1H=0x00;
TCNT1L=0x00;
OCR1AH=0x00;
OCR1AL=0x78;
OCR1BH=0x00;
OCR1BL=0x00;

Autor: Jens123 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi
Vergiss den IO Clock fuer deine Uhr, viel zu ungenau...
Konzentrier dich als Source auf TOSC1 / TOSC2 mit einem Uhrenquarz von
32762kHz..

Die Register stellst du so ein: (MEGA8 / 16)
  ASSR |= _BV(AS2);                  // EXT Clock ROSC1
  TCCR2 |= _BV(CS22) | _BV(CS20);  // Precaler auf 128
  TCNT2 = 0x00;
  OCR2 = 0x00;
  TIFR |= _BV(TOV2);
  TIMSK |= _BV(TOIE2);

Nun frage dich, wo ein fehler sein koennte??
Geh Register fuer Register durch und schau im Datenblatt, was du
jeweils genau einstellst..
Zum testen solltest du den TImer so setzen, dass er jede Sekunde
ausloesst
und in dem Interupt nur eine LED ein / ausschalten lassen.
fannge klein an und nicht gleich mit dem eigenbau eines MP3 Players ;)
Am besten gehst du villeicht sogar einen schritt zurueck nach asm und
bringst da mal einen timer ans laufen und generierst dort eine UHR so
habe ich angefanngen..
als allererst eine LED zum blinken brinngen, dann das LCD Display und
dann alles vereint.
In ASM verstehst du am besten, wie ein µC funktioniert.
Gruss Jens

Autor: ...HanneS... (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Jens,

Du hast ja recht, aber mir scheint, er versteht es nicht und weigert
sich penetrant, ins Datenblatt zu schaun. Nur kein ASM, C ist ja
besser, und wer befasst sich schon mit dem "Schlechteren". Wozu die
Architektur kennenlernen? Muss man doch beim PC auch nicht...

Trotzdem wünsche ich viel Erfolg...
...HanneS...

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.