ATmega16 8-Bit Timer Beispiel
09. November 2011
Das Beispiel soll die Verwendung eines Timer Overflow Interrupts - für den Überlauf des 8-Bit Timers Timer0 des ATmega16 - demonstrieren.
Für Timer0-Takt (8-Bit Timer) wird ein Prescale-Wert von 1024 eingestellt. Dann wird das Bit 0 (TOV0) im Timer Interrupt Register sowie das Bit 0 (TOIE0) im Timer Mask Register auf 1 gesetzt. Anschliessend wird noch das Interrupt-Flag im Statusregister gesetzt. Damit wurden die Voraussetzungen für einen Overflow-Interrupt geschaffen (falls ein solcher Überlauf im Timer0 auftritt, wird die entsprechende ISR abgearbeitet).
Setzt man eine Systemtakt von 1MHz voraus, so kommt es (falls ich mich nicht verrechnet habe) pro Sekunde zu 3,83 Überläufen (ein Überlauf rund alle 262000 Takte). Also wird die ISR grob gesagt 4 mal pro Sekunde ausgeführt.
.include "m16def.inc"
.LIST
.LISTMAC
.CSEG
rjmp start
.ORG OVF0addr ; Nach einem Timer0 Overflow springe
rjmp ISR_TIMER0 ; zu dieser ISR und führe sie aus
.ORG $2A
start:
ldi r16, LOW(RAMEND) ; Stack init.
out SPL, r16
ldi r16, HIGH(RAMEND)
out SPH, r16
ser r16
out DDRA, r16
ldi r16, 0
out PORTA, r16
ldi r16, (1 << CS02) | (1 << CS00)
out TCCR0, r16 ; Prescale-Wert 1024 verwenden
ldi r16, 1 << TOV0 ; Timer Overflow Flag auf den
out TIFR, r16 ; Wert 1 setzen (Überlauf soll
ldi r16, 1 << TOIE0 ; dann einen Timer Overflow
out TIMSK, r16 ; Interrupt auslösen
ser r16
out DDRB, r16
sei ; setze das I-Flag in SREG
loop:
nop
rjmp loop
ISR_TIMER0:
push r16 ; rette akt. Inhalt von R16 auf Stack
in r16, SREG ; lies akt. Inhalt von SREG ein
push r16 ; und rette diesen auf den Stack
in r16, PORTB ; lies PortB aus
inc r16
out PORTB, r16 ; schreibe inkrementierten Wert nach PortB
pop r16
out SREG, r16
pop r16
reti
.EXIT
Für Timer0-Takt (8-Bit Timer) wird ein Prescale-Wert von 1024 eingestellt. Dann wird das Bit 0 (TOV0) im Timer Interrupt Register sowie das Bit 0 (TOIE0) im Timer Mask Register auf 1 gesetzt. Anschliessend wird noch das Interrupt-Flag im Statusregister gesetzt. Damit wurden die Voraussetzungen für einen Overflow-Interrupt geschaffen (falls ein solcher Überlauf im Timer0 auftritt, wird die entsprechende ISR abgearbeitet).
Setzt man eine Systemtakt von 1MHz voraus, so kommt es (falls ich mich nicht verrechnet habe) pro Sekunde zu 3,83 Überläufen (ein Überlauf rund alle 262000 Takte). Also wird die ISR grob gesagt 4 mal pro Sekunde ausgeführt.
Immer noch kein Kommentar. Jetzt wird's aber mal Zeit!
HILFE
Code-Beispiele werden mit den BBCodes [code][/code] dargestellt.
Jedes Tag muss eine Zeile für sich allein haben, d.h der Beispiel-Code
muss wirklich ZWISCHEN den Tags stehen. Beispiel:
Alles was zwischen den beiden Tags [register] und [/register] eingetragen wird, ist nur für registrierte (und eingeloggte) User sichtbar.
[code] ACHTUNG! HIER UMBRUCH WICHTIG. TAG [code] MUSS ALLEIN STEHEN
#include <stdio.h>
int main( void ){
return 0;
} ACHTUNG! HIER UMBRUCH WICHTIG. NACHFOLGENDES TAG [/code] MUSS ALLEIN STEHEN
[/code]Alles was zwischen den beiden Tags [register] und [/register] eingetragen wird, ist nur für registrierte (und eingeloggte) User sichtbar.
Dein Name *
Deine Email
Deine Website
Vorschau