Hallo! :-)
Ich vermute das ich einen Ablauffehler habe durch die Nutzung eines
Unterprogrammes im Interrupt und im Main Programm.
Ich arbeite mit AVR Studio/GGC und einem ATmega 644.
Die Funktion macht einen Vergleich von Variablen und gibt mit 1 oder 0
zurück.
Nun nutze ich diese einmal im Interrupt und in einem bestimmten Zustand
brauche ich den Vergleich auch im Main Programm.
Kann es passieren das da irgenwas aus dem Ruder läuft? Gleizeitiger
Zugriff oder der gleichen?
Wenn ja, muß ich dieses Unterprogramm zur Sicherheit einmal extra für
das Main und einmal für das Interrupt Programm schreiben oder gibt es
einen anderen Weg?
Vielen Dank für Eure Hilfe.
Gruß AVRli...
@ AVRli (Gast)
>Nun nutze ich diese einmal im Interrupt und in einem bestimmten Zustand>brauche ich den Vergleich auch im Main Programm.>Kann es passieren das da irgenwas aus dem Ruder läuft? Gleizeitiger>Zugriff oder der gleichen?
Ja, siehe Interrupt, atomarer Zugriff.
>Wenn ja, muß ich dieses Unterprogramm zur Sicherheit einmal extra für>das Main und einmal für das Interrupt Programm schreiben oder gibt es>einen anderen Weg?
Man kann die Interrupts kurzzeitig sperren.
MFG
Falk
>Kann es passieren das da irgenwas aus dem Ruder läuft? Gleizeitiger>Zugriff oder der gleichen?
Ja, siehe ausserdem Reentranz.
http://de.wikipedia.org/wiki/Eintrittsinvarianz
Wenn du z.B. statische Variablen in der Funktion nutzt, geht es schief,
ebenso bei vielen library-Funktionen.
>Die Funktion macht einen Vergleich von Variablen und gibt mit 1 oder 0>zurück.
Das klingt jetzt nicht so kompliziert, als daß sich das, falls
erforderlich, nicht auch zweimal implementieren ließe.
Oliver
Hallo und danke für Eure Antworten,
ich werde den Vergleich zweimal schreiben. Einmal für den INT und einmal
für das MAIN Programm. Den Platz habe ich schon (nehme ich mir eben)...
Was mich aber viel mehr erschrecken ließ ist folgenes:
Ich habe ebend mir den Abschnitt Interrupt im Beitrag GGC
AVR-GCC-Tutorial durchgelesen. Da stolperte ich über die Aussage das man
Variablen als volatile deklarieren muß um diese gleichzeitig im INT als
auch im MAIN Programm zu nutzen. Ok das habe ich auch immer gemacht! Nur
funktioniert es nach dem was da steht nicht bei Werten die "breiter" als
8 bit sind. Also ein 16 bit Zähler oder einen Struct Variable???
Ohh man da muß ich wohl mein ganzen Programm nochmal durchgehen. :-( Ich
habe schon einige 16bit Zähler die im INT und im MAIN Programm benutzt
werden.
Ist mir bis jetzt auch nie aufgefallen das es zu Problemen führt.
Wie handelt man das nun... :-(
Gruß AVRli...
AVRli schrieb:
> Die Funktion macht einen Vergleich von Variablen und gibt mit 1 oder 0> zurück.
Schreib doch einfach mal die Funktion hin, dann kann man leicht sehen,
obs Probleme geben könnte.
Ein Quelltext sagt mehr als 1000 Worte !!!
Warum die Leute immer ihr Problem erstmal umständlich umschreiben
müssen, statt einfach nur copy&paste.
Peter
AVRli schrieb:
> Ist mir bis jetzt auch nie aufgefallen das es zu Problemen führt.> Wie handelt man das nun... :-(
Benutze mal den neuesten WINAVR, da gibt es ne hübsche "atomic.h", das
ist genau die richtige Medizin für alle diese Probleme.
Aber drauf achten, daß man nicht versehentlich langsame
Funktionsaufrufe, Divisionen, float o.ä. in das atomic mit einpackt,
also wirklich nur die Parameterübergabe.
Peter
> Die Abfrage ist die, die man zweimal schreiben könnte wenn man es dann> muß.
Das bringt aber nicht wirklich viel, denn auch bei zwei Funktionen muss
der Zugriff auf clk_year_long geschützt werden. Der einzige Vorteil ist,
dass dieser Schutz dann nur in einer Funktion nötig ist (in der, die von
main aufgerufen wird), und der Interrupt dadurch geringfügig schneller
ist. Ich würde nur eine Funktion machen, die dann aber inlinen
(insbesondere im Interrupt).
> char not_leap(void)
"char" solltest du nur nehmen, wenn es tatsächlich um Zeichen geht.
Ansonsten "unsigned char" oder "signed char". Oder warum nicht uint8_t?
uint16_t benutzt du doch auch.
Äh, ich frage mich ob eine Berechnung bezüglich eines Jahres nun
wirklich in einem Interrupt geschehen muss. Die Jahreszahl ändert sich
sooooo langsam. Das kann man entweder vorher, so zur Teezeit am 31.12.
berechnen oder irgendwann am 1.1. wenn der Kater verflogen ist.
Das alles scheint mir eher auf einen Designfehler hinzudeuten, wenn es
auch als Lehrstück bzg. volatile usw. hiflreich sein kann.
> Die Abfrage ist die, die man zweimal schreiben könnte wenn man es dann> muß.
Muß man nicht. Probleme gäbe es, wenn die Funktion interne Zustände
speichern würde, die dann bei "parallelem" Aufruf überschrieben würden.
Das ist bei den paar Zeilen aber nicht der Fall.
Oliver
Was spricht dagegen einen einfachen 32 Bit Timestamp im Timerinterrupt
hochzuzählen, statt so ne "Orgie" zu veranstalten? Interruptroutinen
sollten so klein wie möglich sein.
Danke für Eure Antworten!
Kann jemand noch ein Statement zu meiner 16bit Zähler Nutzung geben?
Ich habe auch meine Literatur nochmal durchgeblättert. (C Buch für AVR
controller), da werden 16bit Zähler auch im Main und Interrupt genutzt
und werden auch nur mit volatile "geschützt".
Hmm ich glaube ja bald das ich noch nicht ganz begriffen habe wann es zu
Problemen kommen kann und wann nicht.
Wo kann man sich über die atomic funktion informieren?
Gruß AVRli...
@ AVRli (Gast)
>Kann jemand noch ein Statement zu meiner 16bit Zähler Nutzung geben?
siehe Interrupt.
>Ich habe auch meine Literatur nochmal durchgeblättert. (C Buch für AVR>controller), da werden 16bit Zähler auch im Main und Interrupt genutzt>und werden auch nur mit volatile "geschützt".
Ist unter BESTIMMTEN Umständen möglich, z.B. im Zusammenhang mit dem
Sleep Mode, kann aber auch schief gehen.
>Wo kann man sich über die atomic funktion informieren?
In der Doku der libc, ist irgendwo im WinAVR Verzeichnis is drinnen.
MfG
Falk
Hallo,
na dann werde ich mal meine ganzen Programme durchforsten wo ich 16 bit
Zähler im Int und Main verwende.
Ziel ist es dann immer die Int zu sperren wenn man auf die Zähler im
Main Programm zugreift.
Danke und Gruß AVRli...
>Ziel ist es dann immer die Int zu sperren wenn man auf die Zähler im>Main Programm zugreift.
Vorher ein CLI und hinterher ein SEI...
So behandelt man doch immer Variablen, die "atomic" behandelt werden
müssen.
STK500-Besitzer schrieb:
>>Ziel ist es dann immer die Int zu sperren wenn man auf die Zähler im>>Main Programm zugreift.>> Vorher ein CLI und hinterher ein SEI...> So behandelt man doch immer Variablen, die "atomic" behandelt werden> müssen.