Forum: Mikrocontroller und Digitale Elektronik TIMER bei avr Atmega8+MKII in C


von sutcer (Gast)


Lesenswert?

Hallo Leute!

ich hab jetzt wochenlang das netz durchforscht, werde nur teilweise 
fündig und komm auf keinen grünen zweig, deswegen wär ich froh wenn mir 
hier jemand helfen könnte da ich in dem bereich TIMER grad gar nicht 
parat komm. ich wär froh wenn ich ein passendes oder sich gut 
erklärender quellcodefände.

und zwar würd ich gern folgendes machen:

eine lichtschranke wird unterbrochen (simpler fotosensor), daraufhin 
wird eine LED (grün) eingeschaltet. (das hab ich bereits und 
funktioniert)

jetzt möchte ich gerne, dass wenn die LED bzw. der unterbruch länger als 
eine zeit x andauert, dass eine weitere LED (rot) eingeschaltet wird.

das ist schon alles...

cool wärs natürlich wenn ich dann die hand weg nehme, also lichtschranke 
nicht mehr unterbrochen ist, dass alle LED wieder aus sind.

wär echt ne feine sache, wenn mir jemand unter die arme greifen könnt.
der timer kommt mir gerade vor wie ein baum und ich steh im urwald, 
echt.
hab schon super viel gegoogelt, aber es sind alles nur so häppchen die 
ich nicht recht aneinander reihen kann.

ich danke schonmal im voraus für jegliche hilfe!

bestegrüße!
sutcer

von sutcer (Gast)


Lesenswert?

bzw. wär ich schon heidenfroh wenn mir jemand die timer geschichte 
erklären könnte, an welche stelle vom programm was rein muss und wo ich 
register setzen muss :)

von Heinz (Gast)


Lesenswert?

sutcer schrieb:
> ich danke schonmal im voraus für jegliche hilfe!
>
> bestegrüße!
> sutcer

Alles was du brauchst:http://www.duden.de/rechtschreibpruefung-online

von oldmax (Gast)


Lesenswert?

Hi
In C kann ich leider nicht helfen, aber es gibt hier Tutorials. Schau 
einfach mal unter AVR oben links.
Zum Timer.
Ich benutze ihn fast in jedem Projekt als Zeitbasis. Die Timer-ISR wird 
bei mir alle MSek. aufgerufen. Daraus bilde ich dann alle Zeitimpulse 
die ich brauche, indem ich de mSek. zähle und vergleiche. Dann set ich 
mir ein Flag, welches im Hauptprogramm geprüft, die Bearbeitung erledigt 
und dann wieder zurückgesetzt wird. Ist also kein Problem. Lediglich die 
Initialisierung mußt du durchführen. Da fällt mir grad ein, im 
Datenblatt sind auch Beispiele in C aufgeführt. Vieleicht hilft's.
Gruß oldmax

von oldmax (Gast)


Lesenswert?

Hi
Hab grad gelesen, das dir nicht klar ist, was ein Timer macht, bzw. wie 
du ihn verwendest. Nun, es gibt verschiedene Arten ihn zu nutzen, das 
Datenblatt gibt darüber Auskunft. Um Zeitgesteuerte Aufgaben zu 
erledigen mal ein Beispiel:
Zuerst mußt d die Taktfrequenz deines Controllers kennen, denn der Timer 
zählt jeden Takt automatisch mit. So ist der Timer 1 beim Atmega 8 mit 
einem ein 2 Byte Zählregister ausgestattet. Das erlaubt Zahlen bis 
65535, dann fängt er wieder bei 0 an. Nun hat ein Timer auch einen 
Teiler ( Prescaler) Dies erlaubt, die eingehenden Takte vor Zählung zu 
teilen. Angenommen, dein Controller arbeitet mit 8 MHz und du stellst 
deinen Prescaler auf 8, zählt er theoretisch in einer Sekunde bis 1 000 
000. Das nutz nix, es sei denn, du kannst ihm mitteilen, das du nach 
1000 Impulsen gern ein kleines Programm durchlaufen möchtest. Und das 
macht der Timer Compare Interrupt. Du stellst ein Vergleichsregister auf 
1000-1 ( weil 0 auch ein Schritt ist !) un wählst die entsprechende 
Betriebsart. Nun läuft der Timer bis 1000, erkennt den Vergleich und 
löst einen Interrupt aus, d. h. er ruft springt zu einer festgelegten 
Adrese. Gleichzeitig setzt er das Zählregister wieder auf 0.
An dieser Adresse kann ein RETI ( Return from Interrupt) stehen, oder 
ein Sprung zu einem Programmteil, welches dann mit RETI beendet wird. In 
diesem Programmteil incrementierst du nun eine Variable für die mSek. 
denn das ergibt die 1000000/ 1000. Durch entsprechende Zählung der 
Interrupts, also der Aufrufe deines kleinen Programmes können nun Zeiten 
abgeleitet werden.  Bedenke, in eine ISR gehören nur kleine 
Programmteile, denn schließlich muß ja vor erreichen der nächsten 1000 
im Zählregisteqer die Arbeit erledigt sein. Und das Hauptprogramm will 
ja auch noch sene Arbeit erledigen. Aber keine Angst, bei 8 MHz erledigt 
der Controller ca. 4000 Befehle...
Gruß oldmax

von Karl H. (kbuchegg)


Lesenswert?

sutcer schrieb:
> bzw. wär ich schon heidenfroh wenn mir jemand die timer geschichte
> erklären könnte, an welche stelle vom programm was rein muss und wo ich
> register setzen muss :)

http://www.mikrocontroller.net/articles/FAQ#Timer

Ganz unten: Timer

von sutcer (Gast)


Lesenswert?

Hallo Leute!

Ich danke schonmal für die Hilfe, konnte auch schon ein wenig was damit 
erreichen... steht steh ich aber vor meinem abschließendem problem, 
allerdings nicht der timer selbst, hoff ich. vielleicht kann mir ja 
nochma jemand helfen :-)

also, wenn das eingangssignal an port d eine längere zeit x (von mir aus 
5 sekunden) fehlt, erst dann soll der ausgang port C0 (bei mir eine rote 
LED) geschaltet werden und somit zeigen dass meine 'lichtschranke' zu 
lang unterbrochen war.
zweites problem, ich hab einen taster an port B2 liegen, dieser soll 
eine quittierung werden und ausgang port C0 (rote led) dauerhaft 
ausschalten, bis die lichtschranke wieder zu lange unterbrochen wird. 
derzeit geht sie nur aus, wenn der taster betätigt ist.

hier mal mein kleines programm, dass ich bis jetzt zusammen habe:

#include <avr/io.h>
#include <avr/interrupt.h>
#define F_CPU 1000000UL

ISR( TIMER0_OVF_vect )

{
  static uint8_t swTeiler = 0;

  swTeiler++;
  if ( swTeiler == 250)
  {
  swTeiler =1000000;
  PORTC |= (1<<0);
  }

}
int main ()
{
  DDRB=0x01;                       // B.0 = Ausgang
  DDRB &=~(1<<2);                  // PIN PB1 als Eingang
  PORTB |=(1<<2);                  // internen Pull-Up an PC1 aktivieren
  DDRC = 0x01;                     // B.0 = Ausgang

  ACSR &= ~(1<<7);                 // Comparator einschalten
  sei();                           // globale interrupts freigeben




  while (1)
  {

    if (bit_is_set (ACSR, 5))
    {
    PORTB &= ~(1<<0);             // LED = OFF
    TCCR0  = (1<<CS01);
    TIMSK |= (1<<TOIE0);
    }
    else
    {
    PORTB |= (1<<0);
    }
    if(bit_is_clear (PINB,2))
    {
    PORTC &=~(1<<0);
    }

  }

}

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.