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.
 
    .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:
[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