Keil uvision 4.6 Watch Problem: "not in scope"

Gast #4550907
Lesenswert?

Hallo zusammen,

ich verwende Keil uvision 4.6 und habe ein Problem mit dem Watch 1 
Window. Dort will ich mir beim Debuggen den Wert einer Variable anzeigen 
lassen. Doch das funktioniert nicht so recht, wenn ich eine lokale 
Variable deklariere. Dann kommt beim Debuggen anstatt des Werts die 
Meldung "not in scope".
1
 
2
#include <stm32f4xx.h>
3

4
int main() {
5
  
6
  uint32_t counter=160;
7
  
8
  do{
9
  } while(1);
10

11
}

Das Problem kann ich beheben, wenn ich vor die Variable volatile 
schreibe.
volatile uint32_t counter=160;

Ich verstehe nicht wirklich was das volatile macht und warum es dann 
klappt? Und ist das die einzige Möglichkeit das Problem zu beheben oder 
habt ihr noch Alternativen?
#4550944
Lesenswert?

Hallo Balle,

das Schlüsselwort "volatile" weist dem Compiler an, den Wert der 
Variable nach jeder Veränderung im Speicher abgelegt wird. Damit kann 
der Debugger dann auch dem Wert beobachten. Wenn man dem Compiler die 
Wahl überlässt, werden die Variablen möglichst lange in 
Prozessor-Registern gehalten, um die Zugriffsgeschwindigkeit zu erhöhen 
(Zugriffe auf ein Register gehen schneller - weniger Taktzyklen - als 
Zugriffe auf den Speicher). Außerdem benötigt eine Adressierung eines 
Registers im Vergleich eines Speicherzugriffs auch Weniger Code.

Schau Dir doch mal der erzeugten Code für die beiden Fälle mal im 
Assembler-Fenster an. Dann sollte der Unterschied leicht zu sehen sein.

Grüße
Hoschti
Gast #4550959
Lesenswert?

Danke für deine Erklärung.

Horst V. schrieb:
> nach jeder Veränderung im Speicher abgelegt wird.

Dazu habe ich aber noch eine Frage: In welchem Speicher wird die 
Variable abegelegt? Ich weiß, dass im Flash (nicht flüchtiger) Speicher 
das Programm gespeichert wird und im RAM die Daten. Aber was zählt hier 
wirklich zu Daten? Gehören die Variablen und ihre Werte zum Programm 
oder zu den Daten?
#4551015
Lesenswert?

Aus der Frage schließe ich mal, dass sich Deine Erfahrung in Sachen 
Programmierung noch in Grenzen hält. Was aber jetzt absolut nicht 
negativ gemeint ist!

De Speicherort einer Variablen hängt davon ab, wie sie deklariert ist. 
Die "üblichen" Variablen, die man schreiben und lesen möchte ( so wie in 
Deinem Beispiel von oben), werden im Ram abgelegt. Ram heißt 
ausgeschrieben "random access memory", d.h. Speicher mit wahlfreiem 
Zugriff (also schreiben und lesen).

Deklarierst Du eine Variable als "const", kann der Compiler/Linker sie 
im Rom ablegen, da sie eine Konstante ist, also nur gelesen werden kann. 
Das gilt zumindest erst mal bei Mikrocontrollern. Auf dem PC oder 
ähnlichen Rechnern landen auch "const" Variable im Ram (da ja dort kein 
Rom für die Anwenderprogramme genutzt wird).

Wenn Du da Genaueres wissen willst, schau doch mal in die beim 
Compilieren/Linken erzeugte Map-Datei rein. Da werden normalerweise auch 
die Speicherklassen der Variablen angegeben. Feinheiten dazu musst Du 
aber dann im Handbuch nachlesen.

Horst
Gast #5656840
Lesenswert?

analog schrieb:
> jo... oder man spart sich das ganze Theater und schraubt in den
> Compiler
> Einstellungen das Level auf Level 0 runter... dann wird dir auch deine
> lokale Variable nicht mehr weg optimiert!

Hilft in dem Fall nicht. Der Compiler wird trotzdem lokale Variablen 
wenn möglich im Register halten oder auf den Stack legen. Somit kannst 
du sie nicht auf die globale Watch-Liste setzten (die braucht eine fixe 
Adresse im RAM). -O0 bedeutet übrigens niedrigste Optimierung, nicht 
keine! Einfach wie von hoschti vorgeschlagen mal den generieren ASM Code 
ansehen.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren