Forum: Mikrocontroller und Digitale Elektronik "voaltile" Variabe in ISR


von Fred (Gast)


Lesenswert?

Was hat es zur Folge, wenn ich die Variable i nicht als volatile 
deklarieren würde. Bliebe diese unverändert?

volatile int i=0;

ISR{
i++;
}

main{
  gehe in ISR wenn etwas bestimmtes passiert
}

von Benedikt K. (benedikt)


Lesenswert?

Diese würde ganz normal verändert werden, nur wenn du in einer anderen 
Funktion schreiben würdest
while (i==0);
dann würde die Schleife für immer hängen bleiben, wenn die Variable zu 
Beginn 0 ist.
Das volatile zwingt den Compiler die Variable bei jedem Zugriff neu zu 
lesen und nicht die Lese/Schreibzugriffe wegzuoptimieren.

von Stefan E. (sternst)


Lesenswert?

i würde sich dann auch verändern, nur würde diese Veränderung im 
restlichen Code nicht unbedingt bemerkt werden.

von Fred (Gast)


Lesenswert?

also sowas ginge nicht?

int i=0;

ISR{
i++;
}

main{
  while(true){
     gehe in ISR wenn etwas bestimmtes passiert
     if(i==10) ende programm;
  }
}

von Benedikt K. (benedikt)


Lesenswert?

Das funktioniert nur, wenn i volatile ist.

von Stefan B. (stefan) Benutzerseite


Lesenswert?

Das steht ausführlich im AVR Tutorial. Hier ganz kurz:

Die ISR würde i auch ändern, wenn es nicht volatile wäre. Aber nicht 
notwendigerweise an exakt der gleichen Position innerhalb der ISR. Der 
Compiler könnte Blöcke von Anweisungen umstellen, wenn das Endergebnis 
das gleiche ist. Ein Grund wäre z.B. weil er so besser mit seinen 
Arbeitsregistern haushalten kann.

main kann nicht ohne weiteres "in die ISR gehen". main kann Interrupts 
einschalten und wenn der Interrupt auftritt, wird zwischen zwei 
Maschinenbefehlen - nicht zwischen zwei C Anweisungen - automattisch in 
die ISR verzweigt.

Würde obiges i auch in main benutzt, dann braucht es das volatile plus 
mehr.

Durch das volatile machst du dem Compiler bekannt, dass sich i 
ausserhalb der Kontrolle von main ändern kann. Der Compiler unterlässt 
dann bestimmte Optimierungen, die er machen könnte, wenn sich i 
augenscheinlich in main nicht ändert. Ein volatile i wird jedesmal bei 
Verwendung frisch eingelesen und ggf, auch gespeichert.

Das plus mehr betrifft den Zugriff auf Datentypen, die mehrere Zugriffe 
benötigen (wie z.B. ein int) und mehr. Theoretisch kann ja ein ISR 
auftreten, wenn die Hälfte des Datenzugriffs erfolgt ist. Dann ändert 
die ISR i und das unterbrochene main wird fortgesetzt - mit der zweiten 
Hälfte des Datenzugriffs. Die erste Hälfte ist aber bereits ungültig...

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.