www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Interrupt merken? ATMega128L


Autor: Hans Klemer (losti85)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

ich habe da eine Frage ich benutze einen Atmega 128L. Auf meinem 
Mikrocontroller Läuft ein Timer der nach einer gewissen zeit einen 
Interrupt auslöst und dort eine Funktion aufruft die so ca 100ms dauert. 
In der Zwischenzeit kann aber ein weiterer Intterrupt auftreten. Kann 
man sich diesen Interrupt irgendwie merken und in nach dem Ablauf des 
anderen Interrupts aufrufen. Da dieser den Ersten Interrupt nicht 
unterbrechen darf. Wäre nett wenn jemand mir da helfen könnte Grüße 
Losti

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Falscher Ansatz. Die Interrupt-Routine darf keine 100ms dauern.

Besser: Im Interrupt ein Flag setzen und in der Hauptschleife abhängig 
vom Flag den 100ms Job laufen lassen.

Autor: Sven P. (haku) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Trotzdem ja, ein Interruptflag wird beim Interrupt automatisch gesetzt 
bleibt solange gesetzt, bis die entsprechende Behandlungsroutine 
aufgerufen wurde.

Autor: Lothar Miller (lkmiller) (Moderator) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Wäre nett wenn jemand mir da helfen könnte
Ja, das Datenblatt.
Wenn ein Interrupt enabled ist, bleibt der solange anstehen, bis das 
zugehörige Interrupt-Flag zurückgesetzt wird (und das passiert idR durch 
eine Interaktion der Software).

Autor: Lothar Miller (lkmiller) (Moderator) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Interrupt ... Funktion ... die so ca 100ms dauert.
Das darf nicht sein, das ist eine extrem unsaubere Programmierung.
Denn was nicht gespeichert wird, ist die Information, wie_oft der 
Interrupt (z.B. ein Timer-Überlauf) in dieser Zeit aufgetreten ist. du 
weißt also nach den 100ms nur, dass mindestens 1 mal die 
Interruptbedingung zugetroffen hat.

Autor: Peter Diener (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

korrekter ist es, wenn man eine globale Variable dazu verwendet, sich zu 
merken, dass der Interrupt da war (die Variable setzt man im Interrupt 
auf z.B. 1).
Diese Variable kann man dann im Hauptprogramm oder auch wo anders 
zyklisch abfragen, wenn man gerade Zeit dazu hat und wenn sie gesetzt 
ist, arbeitet man das ab, was der Interrupt auslösen soll. Wenn man das 
gemacht hat, setzt man die Variable zurück, so dass die Routine erst 
beim nächsten Interrupt wieder ausgeführt wird.

So vermeidet man, dass der Interrupt unnötig lange dauert.

Grüße,

Peter

Autor: Falk Brunner (falk)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Siehe Interrupt

Autor: Hans Klemer (losti85)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo danke schonmal für die schnelle Auskunft mein Problem ist 
allerdings das ich sobald der Interrupt auftritt sofort darauf reagieren 
muss also dieser 100ms ablauf erfolgen muss. Mir ist schon klar das das 
sehr unsauber ist aber hat jemand eine andere ideee. Das Problem ist das 
das Hauptprogramm natürlich gerade etwas anderes bearbeiten kann und 
dafür auch etwas zeit braucht. In dem Fall wären von den 100 ms schon 15 
- 25 verbraten. Was auf keinen Fall passieren darf.

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Tja - dann hilft, im 100ms Interrupt Handler die Interrupts wieder 
freizugeben und genug Stack vorzusehen. Ein RTOS oder ein 
top/bottom-half Handler wäre wohl ein zu grosser Schritt.

Autor: Peter (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,
> 100ms ablauf erfolgen muss
kann man nicht die 100ms etwas optimieren? Was dauert denn so lange?

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>sofort darauf reagieren muss also dieser 100ms ablauf erfolgen muss.

Innerhalb dieser 100ms brauchst Du also Mikrosekunden genaues Timing?
Das halte ich für ein großes Gerücht!
Zeig doch mal Deine Interruptroutine; dann relativieren sich Deine 
Anforderungen sofort.

Autor: Hans Klemer (losti85)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Das ist halt ein Zeitschlitz in dem etwas verarbeitet werden muss und 
den muss ich feste einhalten

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>Das ist halt ein Zeitschlitz in dem etwas verarbeitet werden muss und
>den muss ich feste einhalten

Solche Probleme haben die meisten Leute hier, nur daß die Schlitze nicht 
100ms sondern 100µs groß sind.
Aber ich sehe schon, Dein Projekt ist geheim :-)

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>sobald der Interrupt auftritt sofort darauf reagieren
>muss also dieser 100ms ablauf erfolgen muss.

Die Lösung Deines Problems könnte davon abhängen, was mit "sofort" 
gemeint ist. Es macht einen Unterschied, ob es "innerhalb weniger 
Taktzyklen" bedeutet, oder "innerhalb einer Millisekunde", denn ersteres 
ist auch für den µC schnell, letzteres aber noch eher langsam.

Autor: Falk Brunner (falk)
Datum:

Bewertung
0 lesenswert
nicht lesenswert

Autor: Gast (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Da kommt jemand mit Zingeltaskink nicht zurecht und da wird ihm dann 
gleich Multitaskink empfohlen.
Prima Vorschlag!

Autor: Falk Brunner (falk)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@  Gast (Gast)

>Da kommt jemand mit Zingeltaskink nicht zurecht und da wird ihm dann

Single?

>gleich Multitaskink empfohlen.
>Prima Vorschlag!

Und ob. Denn in Wirklichkeit ist auch das Singletasking ein 
Multitasking. UNd  es wird dazu auch ein anderer Denk- und 
Programmieransatz benötigt. Lies mal den Artikel.

MFg
Falk

Autor: Peter Dannegger (peda)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Hans Klemer wrote:
> Hallo danke schonmal für die schnelle Auskunft mein Problem ist
> allerdings das ich sobald der Interrupt auftritt sofort darauf reagieren
> muss also dieser 100ms ablauf erfolgen muss.

Erzähl dochmal, was alles in diesen 100ms passieren muß.
Ich kann nicht glauben, daß diese 100ms voll mit CPU-Berechnungen 
ausgelastet sind.
Und darin liegt auch der Lösungsansatz:

Du hast nach bestimmten Zeiten bestimmte kurze Dinge zu machen.
Dann startest Du einfach nur nen Timerinterrupt mit dem Delayintervall 
für die nächste Sache. Dann machst Du sie und setzt den Timer auf das 
nächste Intervall. In der Zwischenzeit kann sich das Main voll austoben.
Und damit Du weißt, welches nun die nächste Sache ist, nimmst Du eine 
Statemaschine, d.h. eine Variable zählt die States hoch und in ner 
switch/case Anweisung stehen die einzelnen Aktionen.


Anbei mal ein Beispiel, wie so eine Statemaschine im Hintergrund 1-wire 
Sensoren ausliest, ist für nen 8051 in C geschrieben.
Die Statemaschine befindet sich im Timer 0 Interrupt und macht alle 
1-wire Timings.


Peter

Autor: Läubi .. (laeubi) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wenn man ganz fies sein will (geht natürlich nur in ASM wirklich gut:
timer_int:
 ldi temp, HIGH(timer_funktion_100ms)
 push temp
 ldi temp, HIGH(timer_funktion_100ms)
 push temp
reti


main:
.
.
.
rjmp main



timer_funktion_100ms:
.
.
ret

Das reti führt dazu das der AVR zu der timer_funktion_100ms springt, das 
ret am Ende der Funktion springt wieder an die Stelle im Hauptprogram wo 
der Interupt dieses unterbrochen hat.

Autor: Hans Klemer (losti85)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Danke für die Hilfe habt mir gut weitergeholfen. Gruß Losti

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.