Forum: Compiler & IDEs optimiert der Compiler so etwas weg?


von Sven (Gast)


Lesenswert?

Hallo,

ich möchte mein Programm etwas "allgemein und portabel" gestalten. Daher 
möchte ich, je nachdem welche FCPU später verwendet wird, den 
entsprechenden ADC-Vorteiler setzen.

Beispielsmäßig so:
1
#ifndef F_CPU
2
#define F_CPU           16000000UL                   
3
#warning kein F_CPU definiert
4
#endif
5
6
  if (F_CPU == 8000000UL){
7
  ADCSRA = (1<<ADPS2) | (1<<ADPS1);     // Frequenzvorteiler auf 64 einstellen --> 125kHz Abtastrate
8
  }
9
  
10
  
11
  if (F_CPU == 16000000UL){
12
  ADCSRA = (1<<ADPS2) |(1<<ADPS1) | (1<<ADPS0);     // Frequenzvorteiler 128 auf einstellen --> 125kHz Abtastrate
13
  }

Optimiert der Compiler so etwas weg? FCPU ist ja schon zur Compilzeit 
fest und verändert sich während der Laufzeit nicht. Oder wird die 
if-Anweisung tatsächlich während der Laufzeit erst behandelt?

Danke.

von (prx) A. K. (prx)


Lesenswert?

Wird vom Compiler wegoptimiert.

Wenn keine syntaktischen Probleme dagegen sprechen, dann sollte man an 
Stelle von hässlichen #if/#else Orgien solchen lesbareren C Code 
verwenden.

von Wolfgang (Gast)


Lesenswert?

Sven schrieb:
> Optimiert der Compiler so etwas weg?

Das hängt davon ab, was du als Optimierungsstufe gewählt hast. In 
solchen Fällen kann man einfach im List-File (.LSS) nachsehen, was der 
Compiler daraus generiert hat.

von Troll (Gast)


Lesenswert?

Naja aber unbenutzer Code, der niemals zur Ausführung kommt sollte 
mindestens ein Warning bringen und nachträglich vom Compiler, sobald 
irgendeine Optimierung drin ist, wegoptimiert werden.

von (prx) A. K. (prx)


Lesenswert?

Sowas wirft GCC auch ganz ohne eingeschaltete Optimierung raus.

von (prx) A. K. (prx)


Lesenswert?

Troll schrieb:
> Naja aber unbenutzer Code, der niemals zur Ausführung kommt sollte
> mindestens ein Warning bringen

Lieber nicht, sonst wirkt man einer sauberen Programmierung entgehen. 
Denn obiger Code ist weit lesbarer, als der Ersatzcode mit 
Präprozessor-#if statt C-if.

GCC liefert daher auch mit -Wall keine Warnung.

von Klaus (Gast)


Lesenswert?

A. K. schrieb:
> Lieber nicht, sonst wirkt man einer sauberen Programmierung entgehen.
> Denn obiger Code ist weit lesbarer, als der Ersatzcode mit
> Präprozessor-#if statt C-if.
>
> GCC liefert daher auch mit -Wall keine Warnung.

Ist ja auch klar. Denn der COde ist erreichbar. Je nach Wert von FCPU. 
Nicht erreichbarer Code ist per Definition Code der niemals erreicht 
werden kann. Also nicht mehr Wert als toter Zeichensalat. Dann, und nur 
dann, schmeißt der GCC eine Warnung, wenn er so eine Codestelle erkannt 
hat.

von (prx) A. K. (prx)


Lesenswert?

Klaus schrieb:
> Ist ja auch klar. Denn der COde ist erreichbar.

Ist so ein Code auch erreichbar?

if (0) {
   g();
}

von Coder (Gast)


Lesenswert?

In diesem Zusammenhang sind bzw. waren static und const gute Gehilfen.

von Klaus (Gast)


Lesenswert?

A. K. schrieb:
> Ist so ein Code auch erreichbar?
>
> if (0) {
>    g();
> }

Entschuldige bitte, ich war etwas zu schnell mit meinen Gedanken. Du 
hast natürlich Recht. Denn der GCC bekommt das ja mit eingesetzter 
Konstante (nach dem Präprozessor) geliefert. Damit ist das Beispiel mit 
FCPU das gleiche wie if (0) .

Warum gibts denn da keine Warnung vom GCC? ;-)

von Christian B. (casandro)


Lesenswert?

Naja in dem Beispiel ist es ganz einfach.
Aus dem Preprozessor kommt

  if (16000000UL == 8000000UL){
  ...
  }

  if (16000000UL == 16000000UL){
  ...
  }

raus, was im nächsten Schritt zu 0 und 1 zusammen gefasst wird, und die 
ifs fliegen raus.

Was anderes wäre es, wenn Du eine globale Variable hast, denn da gibt es 
für den Compiler keine sichere Methode festzustellen, ob die Verändert 
wurde oder nicht. (da gibts aber auch Möglichkeiten dem Compiler zu 
sagen was Du willst)

von (prx) A. K. (prx)


Lesenswert?

Klaus schrieb:
> Warum gibts denn da keine Warnung vom GCC? ;-)

Weil es keinen Sinn ergibt, die Leute bei völlig normalem Code in 
sinnlosen Warnungen zu ersäufen.

Denk auch an Fälle wie
  inline void f(int x) { if (x) { ... } ... }
  void g(void) { f(0); }
Der Compiler sieht da if(0) mit und if(?) ohne Inlining.

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.