Hallo Leute!
Ich programmiere schon seit einiger Zeit Microprozessoren in C. Wenn ich
nun eine Variable hatte, auf welche ich aus dem Hauptpgrogramm und aus
einer IRQ-Routine zugreifen wollte, habe ich die Codeoptimierung mittels
"volatile" abgeschaltet.
1
volatileuint16_ttest=0;
Nun bin ich aber dabei, dass ich meine ersten Gehschritte in C++ mache.
Hier ist es möglich, ganze Klassen als Volatile zu instanziieren. Ich
verstehe nicht, warum nach einer "volatile"-Instanziierung der Klasse
auch die Methoden von "volatile" sein müssen, falls sie benutzt werden.
In C bezieht sich das "Volatile" ausschließlich auf Variablen
(Datentypen) und nicht auf Funktionen.
1
classauto
2
{
3
public:
4
uint16_tgeschwindigkeit;
5
uint16_tfarbe;
6
uint16_tgewicht;
7
8
uint16_tblinker_ein(uint16_tvar);
9
uint16_tblinker_aus(uint16_tvar)volatile;
10
}
11
12
...
13
14
intmain(void)
15
{
16
volatileautov_a1;
17
autoa2;
18
19
v_a1.blinker_ein(10);// Compilerfeher
20
a2.blinker_ein(10;// Okay
21
22
v_a1.blinker_aus(10);// Okay
23
a2.blinker_aus(10);// Okay
24
25
...
Warum, muss wie in diesem Beispiel gezeigt, die Methode "blinker_ein"
mit Volatile deklariert werden und was macht "Volatile" mit der Methode?
Vielen Dank im Voraus.
Schöne Grüße
Martin
auto ist ein Schlüsselwort. Nenn die Klasse anders (aber nicht if, else,
for, typedef, volatile, unsigned, main oder so, das sind alles
Schlüsselworte in C/C++).
Martin schrieb:> int main(void)> {> volatile car v_a1;> car a2;
ich habe das gefühl das du den Sinn von volatile nicht 100% verstanden
hast. Warum willst du hier die Variable v_a1 volatile machen? du kannst
sowieso nicht aus einer ISR darauf zugreifen weil sie in main lokal
deklariert ist.
Das ganze macht nur bei globalen Variaben einen sinn. (bzw. globalen
objekten)
Martin schrieb:> Ich> verstehe nicht, warum nach einer "volatile"-Instanziierung der Klasse> auch die Methoden von "volatile" sein müssen, falls sie benutzt werden.
Der Code der Methode ist für alle instantiierten Objekte der Gleiche.
Wie kann nun also dieser Code anhand des ihm übergebenen this-Pointers
sehen, ob das Objekt volatile ist, oder nicht? Er kann es schlicht
nicht. Mit dem volatile sagst du der Methode, dass sie "ihr" Objekt
grundsätzlich als volatile ansehen soll. Und von einem volatile-Objekt
kannst du dann natürlich nur volatile-Methoden aufrufen, eben weil nur
diese von einem volatile-Objekt ausgehen und damit entsprechenden Code
enthalten.
Aber ich verseht nicht, wozu das notwendig ist, dass Methoden ihr Objekt
als "volatile" ansehen sollen.
Geht es nicht vielmehr nur um die einzelnen Attribute (z.B.
geschwindigkeit, farbe, gewicht), dass diese ohne Verzögerung in den
Speicher geschrieben oder vom Speicher geholt werden sollen, damit eine
IRQ-Routine ebenfalls darauf zugreifen kann?
Was ist so wichtig daran, dass die Metode selbst als "volatile"
gekennzeichnet wird?
Wenn ich z.B.
1
#include<stdint.h>
2
3
classcar
4
{
5
public:
6
volatileuint16_tgeschwindigkeit;
7
volatileuint16_tfarbe;
8
volatileuint16_tgewicht;
9
10
uint16_tblinker_ein(uint16_tvar);
11
uint16_tblinker_aus(uint16_tvar);
12
}
13
14
cara1;
15
16
intmain(void)
17
{
18
19
a1.blinker_ein(10);
20
21
...
In diesem Beispiel instanziiere ich zwar das Objekt "a1" nicht mit
"volatile", aber die drei Attribute in der Klasse selbst sind mit
"volatile" gekennzeichnet. Auf diese Weise kann ich aus einer
IRQ-Routine ohne Probleme auf diese Attribute zugreifen, ohne, dass das
ganze Objekt als "volatile" instanziiert werden muss und die Methoden
muss man auch nicht separat kennzeichnen.
Ich verstehe die Vorteile und Nachteile zwischen den beiden Beispielen
nicht.
Entschuldigt, meine Unwissenheit, ich stehe in C++ noch ziemlich am
Anfang.
Martin schrieb:> dass diese ohne Verzögerung in den Speicher geschrieben> oder vom Speicher geholt werden sollen, damit eine> IRQ-Routine ebenfalls darauf zugreifen kann
Das hat überhaupt nix mit IRQ, Optimierung oder "verzögerungen" zu tun,
sondern sagt einfach nur dem Compiler, dass sich die Variable außerhalb
seines Sichtbereiches jederzeit ändern kann, oder das schreiben auf
diese für den Compiler nicht vorhersehbare Seiteneffekte hat.
Dasd führt dann dazu, dass bestimmte Optimierungen/Änderungen nicht
durchgeführt werden dürfen.
das ist in Analogie zum const qualifier durchgezogen
class A {
void foo();
void bar()const;
};
A a;
a.foo() => ok
a.bar() => ok
const A a;
a.foo(); => not ok
a.bar(); => ok
Ist auch sinnvoll so. Dadurch können für Objekte, die volatile sind,
auch nur Memberfunktionen, die als volatile deklariert sind, aufgerufen
werden. Nur in denen ist auch sichergestellt, daß die Anforderungen, die
volatile an den vom Compiler erzeugten Code stellt, auch erfüllt sind.
Vielen Dank für eure Antworten!
Ich werde mich noch eingehender mit dem Thema beschäftigen, aber ihr
habt mich mit euren Erklärungen bereits ein die richtige Richtung
geführt.
Schöne Grüße
Martin
Eine eigene Frage?
Dieser Thread ist über 14 Jahre alt.
Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.