Software – Magie oder ?

An manchen Tagen zeigt sich die magische Seite der Softwareentwicklung. Magisch ist alles, was dem Ungelernten verborgen ist. Manchmal aber glauben auch die Gelernten und die, die meinen etwas gelernt zu haben, an Magie.

An diesem Montag verhielt sich die Software anders als am Freitag. Von den schönen Bildern, die ich im letzten Beitrag schilderte, zeigte sich keines.

Magisch war an dieser Stelle noch nichts. Immerhin verwendete die Software Teile von anderen Projekten und bei einem neuerlichen Zusammenbau am Montag konnte es passieren, dass eben etwas nicht stimmte.

Obwohl? Unsere Oberfläche hat ihre eigenen Icons, die von unserem UX-Designer gemalt wurden. Warum nur wurden sie nicht gefunden?

Ich forschte den ganzen Tag. Am Ende zeigten sich die Bilder wieder. Die Ursache schien aber magisch zu sein!

Der erste Teil — Debuggen und so

Wenig später meldeten sich Kollegen, dass die Icons verschwunden waren. Am Montag schon so gefragt zu sein, erleichtert das Einfinden in die Arbeitswoche.

Ich baute die Software im Debug Modus und nun prüfte das System die Zusicherungen und meldete diverse „Assertion Errors”. Schnell verriet es die Stelle, die schieflief. Die Bilder wurden gesucht, aber dann doch nicht geladen.

Was war hier los? Stimmten die resource dlls? Enthielten diese die korrekten Icons?

Es gab in der letzten Woche Probleme mit der Versionsverwaltung. Sollte hier das Problem liegen? Musste das am Montag sein? Eine Kontrolle der Quellen zeigte nichts Auffälliges. Alles stimmte mit dem Stand von Freitag überein.

Wenn das am Freitag lud, musste das auch am Montag laden!

Nach dem Frühstück nahm ich mir vor, den Freitag zu vergessen und das Problem zu lösen. Ich setzte einen Breakpoint am Anfang der Ladesquenz und ließ die Software von API Aufruf zu API Aufruf laufen, bis etwas nicht mehr funktioniert.

Ich kam an diese Stelle:

int vsize = SizeofResource(NULL, hsrc);

Die Variable vsize gab die Größe des Bildes an, das vom Icon gelesen werden soll. Je nach Auflösung wären das 16×16 bis 48×48 Bits. Der Debugger zeigte einen Wert von 0.

Das war das Problem. Ein Blick in MSDN erklärte die Parameter. Der erste bestimmt den Ort der Resourcen. Waren diese im Hauptprogramm oder in einer dll? Der Wert NULL bedeutete Hauptprogramm. Das schien verkehrt zu sein, da die Software in Zeilen davor eine hInstance Variable verwendete.

Ich änderte NULL in hInstance:

int vsize = SizeofResource(hInstance, hsrc);

Nun hatte vsize den Wert von 96. Das sah besser als 0 aus, war aber immer noch verkehrt. Die schönen Bilder zeigten sich nicht. Bei 32 Bit Pixeln war ihre Bitmap einfach größer.

An dieser Stellte holte ich mir eine Flasche Mineralwasser aus der Ausgabe in der Mitte des Gebäudes. Mit Bewegung verändert sich immer der Blickwinkel und eine Idee musste her.

Das Umfeld der Funktion sah schon merkwürdig aus. Es waren mehrere HANDLEs deklariert. Mir fiel die Zeit von 1995 ein. Damals war alles ganz anders. Wie war das mit den Icons in der ganz alten Zeit? Im letzten Jahrtausend?

Das war noch eine 16-Bit Welt. Speicherplatz war ganz knapp. Die Resourcen waren kostbar. Icons mit ihrer Sammlung von Bilder in verschiedenen Auflösungen, von denen sowieso nur eines gebraucht wurde, kamen später dazu. Der Weg zum richtigen Bild erfolgte in zwei Schritten. Zunächst ein HANDLE für das Verzeichnis anlegen, dann dieses einlesen. Hier nach dem richtigen Bild fahnden, dann ein HANDLE für das Bild anlegen, damit zum Schluss die Pixel eingelesen werden können.

Sah doch ganz einfach aus. Warum klappte das nicht?

Nach einem Schluck Mineralwasser waren die Augen wieder klar. Das Handle hsrc, war das für das Verzeichnis der Bilder. Für das eigenliche Bild gab es das Handle hrSrc.

Das funktioniert dann:

int vsize = SizeofResource(hInstance, hrSrc);

Magie oder was?

Warum funktionierte das am Freitag?
Hatte ich die Bilder halluziniert?
Zum Glück bestätigten meine Kollegen die Bilder. Sie hatten die Bilder auch gesehen. Aber mit dem Source, der am Freitag durchlaufen wurde, konnte das nie funktioniert haben.
Konnte es sein, dass die Bilder an unterschiedlichen Stellen gelesen werden?
In gewachsenem Code sind Funktionalitäten durchaus mehrfach und auch ähnlich implementiert. Dann wäre am Freitag an einer anderen Stelle zum Einlesen der Icons durchlaufen worden. Aus irgendeinem Grund war dies am Montag dann nicht mehr der Fall.
Gespannt suchte ich nach „SizeofResource” in den Quellen. Es kam leider nur einmal vor.
Danach suchte ich nach  „icon“. Da gab es einiges. Interessiert las ich die gefunden Zeilen. Meistens wurden sie weitergeben und angezeigt. Gelesen wurden sie aber nur in dem Zeilen, die auch Freitag niemals funktionieren konnten.
Was nun?
Die Kollegen meinten dazu: Problem gelöst, einchecken und weitermachen.
Mich erinnerte das an Voodoo oder Zauberei. Diese Hexer wussten ja auch nie, was sie taten und wenn es dann funktionierte, dann war ein Zaubertrank geboren. Das entsprach so gar nicht meinem Selbstverständnis von einer Ausbildung als Ingenieur.
Am nächsten Morgen erklärte eine Email, dass mit den Microsoft Patches die Anzeige von Icons nicht mehr so richtig funktioniert. Zu ändern wäre genau die Zeile mit dem „SizeOfResource”. Hier könnte man die Größe der Bitmap einfach selber ausrechnen.
Ich vermute mal, dass die Jungs vom Microsoft bei NULL einfach die Größe der zuletzt gelesenen Resource zurückgaben, anstatt diese in der Applikationsressource zu suchen. Der letzte Patchday korrigierte das.

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert