Aus dem Maschinenraum
Heute mal wieder so ein paar schöne WTF-Momente gehabt. Das ist zwar bei Wordpress nix neues, weswegen ich heute auch mit Serendipity experimentiert hab. Das ist zwar toll, aber die Permalinkstruktur gefällt mir nicht wirklich, und der Import hat auch nicht geklappt (konsquent falscher Zeichensatz). Ist aber hier nicht das Thema
Was mich heute zum wiederholten Mal verwundert hat, sind spontan nicht mehr funktionierende PHP-Skripte.
PHPExec meinte doch eben völlig unmotiviert (”I didn’t touch anything! *looks away*”), mir einen Fehler zu melden, eine Variable wäre nicht initialisiert. Das war sie zwar wirklich nicht, aber das Skript lief ohne Unterschied literally seit Jahren. Fehlerfrei. Ich hab eine glaubhafte Versicherung meines Hosters, dass er auch nix gemacht hat…
Sowas hatte ich schonmal: ein Datenbank-Wrapper, der schon Wochenlang genutzt wurde, meinte auf einmal, Bind-Variablen nicht mehr richtig übergeben zu wollen. Und Überraschung: laut Manual hätte es nie funktionieren können.
Hatte schonmal jemand ähnliche Effekte? Plötzlich veränderliches Verhalten ist etwas, was ich mir so gar nicht erklären kann.
Optimierung mal anders
Aus der Kategorie, “Spaß am Gerät, den man lieber nicht hätte”: Amoklaufende Optimierung im GCC.
Man lese folgenden Code, der alternierend ein LCD mit Zahlen, Buchstaben und “nichts” füllt:
while (1) { for (unsigned char k=0;k<4;k++) { LCD_setCursorPos(k,0); LCD_write("1234567890123456"); } delay(250); LCD_clear(); delay(250); for (unsigned char k=0;k<4;k++) { LCD_setCursorPos(k,0); LCD_write("abcdefghijklmnop"); } delay(250); }
What could possibly go wrong
Gut, wir kennen ja Murphy: Alles, was schief gehen kann, geht schief. Und wenn schon der Code kaum Fehlerpotential hat, muss zwangsläufig der Compiler seinen Beitrag dazu leisten
Genau das hat er dann auch getan… erstmal äußerte sich das ganze dann darin, dass wider erwarten nur Zahlen, leere Seite und wieder Zahlen kamen. Und dabei die Seite mit den Zahlen irgendwie “zu lang” zu sehen war.
Was war also los?
Wie in Blick in das praktischerweise im Makefile angeforderte Extended Listing verrät, ist avr-gcc der Meinung, die beiden Schleifen würden das Gleiche machen, und kombiniert die in eine Schleife. Durch Ausprobieren anderer Optimierungsstufen zwischen -Os und -O1 kann man dann gcc immerhin überreden, nicht mehr beides in einer Schleife zu erledigen, sondern die zweite komplett zu ignorieren (toll!)… auch nicht ganz das Wahre. -O0 erzeugt Warnungen in <util/delay.h>, fällt also leider aus.
Die einzige mir bekannte Lösung ist das verlegen der beiden Schleifen in separate Methoden:
void test1(void) { for (unsigned char k=0;k<4;k++) { LCD_setCursorPos(k,0); LCD_write("1234567890123456"); } delay(250); } void test2(void) { for (unsigned char k=0;k<4;k++) { LCD_setCursorPos(k,0); LCD_write("abcdefghijklmnop"); } delay(250); }
while (1) { test1(); LCD_clear(); delay(250); test2(); }
Gut, man muss eingestehen, der gcc hier ist schon etwas (avr-gcc (WinAVR 20080610) 4.3.0) älter. Das ist in einigen Kompatibilitätsproblemen mit anderen Projekten geschuldet, die sich auf ein bestimmtes Verhalten verlassen (hey, ich hab das nicht erfunden, ok?)
Kann also sein, dass das mittlerweile nicht mehr so ist. Aber trotzdem toll, dass so ein Bug es tatsächlich in eine Produktiv-Version schafft. Ist das kein Testcase? Naja, gcc halt…
Chemiestunde
Willkommen zum monatlichen Alibi-Beitrag
Heute mal ein wenig Bildung direkt “aus dem Leben”. Zumindest aus meinem…
Wenn der Kaffee langsam komisch schmeckt, sollte man sich – grade wenn man in für Kalkhaltiges Wasser bekannten Gegenden wohnt – durchaus mal mit der Heizwendel des Wassererhitzungsgeräts beschäftigen. (mehr…)
