Betrachten Sie diesen einfachen Code:
void g();
void foo()
{
volatile bool x = false;
if (x)
g();
}
Sie können sehen, dass der potenzielle Anruf an weder optimiert gcc
noch clang
optimiert wird g
. Dies ist nach meinem Verständnis richtig: Die abstrakte Maschine geht davon aus, dass sich volatile
Variablen jederzeit ändern können (z. B. durch Hardware-Zuordnung), sodass ein konstantes Falten der false
Initialisierung in die if
Prüfung falsch wäre.
Aber MSVC eliminiert den Aufruf von g
vollständig (das Lesen und Schreiben bleibt jedoch erhalten volatile
!). Ist das standardkonformes Verhalten?
Hintergrund: Ich verwende gelegentlich diese Art von Konstrukt, um die Debugging-Ausgabe im laufenden Betrieb ein- und ausschalten zu können: Der Compiler muss den Wert immer aus dem Speicher lesen. Wenn Sie also diese Variable / diesen Speicher während des Debuggens ändern, sollte der Steuerungsfluss entsprechend geändert werden . Der MSVC-Ausgang liest den Wert erneut, ignoriert ihn jedoch (vermutlich aufgrund ständiger Faltung und / oder Eliminierung toten Codes), was meine Absichten hier natürlich zunichte macht.
Bearbeitungen:
Die Eliminierung der Lese- und Schreibvorgänge
volatile
wird hier erläutert: Darf ein Compiler eine lokale flüchtige Variable optimieren? (Danke Nathan!). Ich denke, der Standard ist völlig klar, dass diese Lese- und Schreibvorgänge stattfinden müssen . Diese Diskussion behandelt jedoch nicht, ob es für den Compiler legal ist, die Ergebnisse dieser Lesevorgänge als selbstverständlich zu betrachten und auf dieser Grundlage zu optimieren. Ich nehme an, dass dies im Standard unter- / nicht spezifiziert ist , aber ich würde mich freuen, wenn mir jemand das Gegenteil beweisen würde.Ich kann natürlich
x
eine nicht lokale Variable erstellen, um das Problem zu umgehen. Diese Frage ist eher aus Neugier.