The case of GrfBuilder

Juli 6th, 2010 by Sirius_White

Everade trug mir gerade ein recht skuriles Problem vor: Mit Harmony verschlüsselte Dateien ließen sich nicht mit GrfBuilder packen. Die Dateien würden einfach übersprungen. Die originalen Dateien hingegen würden wunderbar funktionieren.
Erste Reaktion: Wie soll das gehen? GrfBuilder sollte die Dateien schließlich neutral behandeln und unabhängig von Inhalt packen. Allerdings ließ sich das Problem mit den besagten Dateien tatsächlich nachbilden. Seltsam..

Wie man sehen kann fehlen die größeren Dateien. Könnte es sein, dass er die Dateien aus irgendeinem Grund wirklich gar nicht erst liest? Kein Problem – einfach mal einen auf Mark Russinovich machen und Process Monitor anschmeißen:

Das sieht schonmal interessant aus! Man kann erkennen, dass alle Dateien geöffnet (CreateFile) und auch vollständig gelesen (ReadFile) werden. Einen wichtigen Unterschied gibt es jedoch: Nachdem die beiden funktionierenden Dateien gelesen sind wird in die test.grf geschrieben (markierte WriteFile Einträge). Offenbar werden Änderungen sofort in die GRF geschrieben. Bei der GND Datei fehlt aber dieser Schritt. Der Fehler liegt also irgendwo zwischen dem Einlesen der Daten und dem Schreiben in die GRF.
GrfBuilder ist ein speziell für RO entwickeltes Tool. Könnte es also sein, dass die Dateiformate überprüft werden, bevor eine Datei in die GRF gepackt wird? Durch die Verschlüsselung würden hier zwangsläufig Fehler entstehen. Theoretisch sollte das nicht so sein, aber wer weiß. Also folgende 2 Testläufe:

  • Die Dateien umbenennen (.bin, .txt), den Inhalt beibehalten
  • Die Formatheader einer gültigen GAT/GND Datei an den Anfang der verschlüsselten Dateien kopieren, Inhalt und Name beibehalten

Ergebnis: Der erste Testlauf brachte keine Ergebnisse, die Dateien wurden weiterhin ignoriert. Bei der zweiten Methode wurde nun jedoch eine Datei akzeptiert – die GND mit GAT Header. Interessant hierbei ist, dass ein Ändern des Inhaltes zum Erfolg geführt hat, obwohl der Dateityp mit dem verwendeten Inhalt eigentlich nichts zu tun hat. … Könnte es sich um Kompressionsproblem handeln?
Mit der höchsten Komprimierungsstufe wurde ein andere Datei (GAT mit GND Header) erfolgreich hinzugefügt. Und an dem Punkt kam mir der entscheidende Verdacht: Dateien innerhalb der GRF sind komprimiert. Kompression funktioniert umso besser, je mehr wiederkehrende Strukturen vorhanden sind. Durch Verschlüsselung werden diese Strukturen jedoch zerstört, was eine Kompression schwierig bis unmöglich macht. Nun könnte es sein, dass der zur Kompression verfügbare Speicher zu klein ist, weil eine zu hohe Kompressionsrate erwartet wird, die Dateigröße sich durch die zerstörte Struktur jedoch nicht verringert, sondern vergrößert. Ein Blick in den Source Code der verwendeten GRF Library bestätigte diese Vermutung:

    // 1. Compress file, to have its size
    ptr_comp = malloc(size+100);
    if (ptr_comp == NULL) return NULL; /* out of memory? */
    comp_size = zlib_buffer_deflate(ptr_comp, size + 100, ptr, size, handler->compression_level);

Der Entwickler hat wohl angenommen, dass unter keinen Umständen die Datei sich durch die Kompression um mehr als 100 Bytes vergrößert. Das könnte hier jedoch der Fall sein. Der entsprechende ASM Block war auch schnell gefunden:

Wenn man hier eine größere Zahl addiert sollte man den Bug zumindest umgehen können. Da man mit dem verwendeten Befehl maximal 127 addieren kann, habe ich den Codefluss einfach auf dir davor liegende Funktion (Datei umbenennen) umgeleitet, dort addiert und einen Rücksprung platziert.
Eine bessere Lösung wäre es übrigens, nicht einfach wild drauf los zu schätzen, sondern compressBound zu verwenden:

    The compressBound() shall return a value representing the upper bound of an array to allocate to hold the compressed data in a single call to compress() or compress2(). This function may return a conservative value that may be larger than sourceLen.

Im Fall von Everade genügte aber vorerst mein “Hackfix”. Mit der modifizierten grf.dll kann man nun zwar keine Dateien mehr umbenennen, aber dafür alle Dateien problemlos komprimieren. :)

The case of RCX

Juni 21st, 2010 by Sirius_White

Harmony ist dafür da, Fremdsoftware zu blockieren. Das tut es auch recht gut. Problematisch wird es nur, wenn man ein Programm explizit unterstützen muss… Die Rede ist von RCX – einer japanische Erweiterung des RO Clients, die vielen “alten Hasen” unter RoCha bekannt sein dürfte. Ansonsten verschafft dieses Video einen recht guten Überblick über die Features:

Ein Kunde sprach mich vor kurzem darauf an, dass RCX nicht mit Harmony kompatibel sei. Nicht verwunderlich, schließlich lädt RCX nicht nur eine fremde DLL, sondern fängt auch Winsock Funktionen ab, um anhand der Netzwerkpakete beispielsweise Skilleffekte anzuzeigen. So begann also mein Odysee hin zu einem RCX Fix…

Nach kurzer Codeanalyse stellte sich heraus, warum andere Bot-Protections keine derartigen Probleme haben: Die Netzwerkfunktionen arbeiten nicht direkt auf WinAPI Ebene – RCX umgeht sie daher dezent. Da Harmony auf mehreren Layern arbeitet und alle davon unter RCX liegen gestaltet sich die Sache etwas schwieriger.
Mein finaler Plan:

  • Über Whitelisting wird der RCX DLL der Zugriff auf Harmony gestattet
  • Ein- und ausgehende Netzwerkpakete werden gesammelt und über emulierte Winsock Aufrufe an RCX übergeben
  • ????
  • Profit!

Punkt 1 war schnell erledigt. Die Emulation der Winsock Aufrufe wurde etwas ekelhafter: RCX fängt alle Winsock Aufrufe ab und muss daher selbstständig die originalen Funktionen aufrufen. Bei eingehenden Paketen würde RCX also selbstständig “nachfragen”, ob Pakete vorhanden sind, feststellen, dass dem nicht so ist und einfach mal nichts tun. Ich durfte daher die originalen Winsock Funktionsaufrufe ebenfalls abfangen und RCX mit meinen Daten füttern. Dazu kommt, dass einige Harmony Layer den RO Client derart modifizieren, dass eine Rekonstruktion der originalen Pakete nur mit erheblichem Aufwand möglich ist. Yay.

Im Endeffekt konnte ich den Code auf ~300 Zeilen (und 8 Stunden Arbeit…) kürzen, trotzdem denke ich lieber nicht so oft daran, was bei aktiviertem RCX Fix mit Netzwerkpaketen angestellt wird:

Omnipost!

Mai 30th, 2010 by Sirius_White

Wie betitelt man einen Post, in dem es um alles mögliche geht? Keine Ahnung. Ich nenn ihn jetzt einfach Omnipost.

Was gibts Neues?

Green Mile
Einem Hinweis von Shinryo folgend habe ich mir vor einigen Tagen Green Mile angeschaut. Es geht um einen Gefängniswärter in den 1930er Jahren, der für den Todestrakt der Anstalt, die “Green Mile”, verantwortlich ist. Nachdem er im Laufe der Jahre bereits viele Exekutionen vollstreckt hat, beginnt sich mit der Einlieferung des mysteriösen John Coffey jedoch einiges zu ändern. Der Neue besitzt die wundersame Gabe, Menschen von Ihren Leiden befreien zu können.
Es gibt wirklich wenige Filme, die mich emotional erreichen. Meine Haupterkenntnis nach Titanic war, dass ich irgendwann eine Kreuzfahrt machen möchte. Green Mile hingegen hat es geschafft, mich selbst bei der “Wunderheilungsgeschichte” eines “Gotteswunders” mitfühlen zu lassen. Und genau dafür wird mir dieser Film wohl noch auf Jahre positiv in Erinnerung bleiben. Mein Dank an Shinryo und der Appell an all die anderen, sich diesen Film unbedingt anzusehen!

Hardware 1 : 0 Me
Ich war vor 2 Wochen in Hamburg. LAN-Party bei T-Bash, mit einigen anderen Hamburgern und Sirius_Black. Wir haben zwar nichtmal die Hälfte der geplanten Spiele geschafft, aber die meisten waren dennoch sehr lustig. Begleitet wurde die LAN natürlich – wer hätte es anders erwartet – von diversen technischen Problemen. Eine Maus ist gestorben, kein Spiel hat auf Anhieb bei allen funktioniert und ich hatte das Vergnügen mit Bluescreens. LAN-Party halt.
Aus Faulheit habe ich meinen Rechner per Post zurück geschickt und zurück in Eisenach die Systemplatte in meinen alten Rechner eingebaut. Bluescreens. Was zum..?
Logische Schlussfolgerung: Platte kaputt. Da ich eh vor hatte, die mittlerweile 3 Jahre alte Platte in naher Zukunft auszutauschen, habe ich mir daraufhin 2x 250GB 2,5″ Festplatten und ein neues Gehäuse gekauft. Es ist echt faszinierend, wie viel Speicher man in der Größe (und dem Gewicht!) einer Zigarettenschachtel unterbringen kann.
Als das Mindfactory Paket angekommen war also alles in den neuen Rebel 9 (siehe Bild) eingebaut und eingeschaltet. Lüfter drehen am Rad (na, krieg ich ein Bienchen für dieses Wortspiel?) und ansonsten … passiert nichts. Nach einigen Tests die Erkenntis: Mainboard schrott. Super! Nach kurzem Suchen habe ich sogar noch die Rechnung gefunden – Juli 2009 gekauft. Allerdings nicht bei Mindfactory, sondern bei Compuland. Über Google ließen sich schnell negative Berichte bzgl. der Gewährleistungshandhabung finden. Naja, was solls. Einfach mal probieren. Und, wer hätte es anders erwartet:

Hiermit bestätigen wir Ihnen den Erhalt der Ware, leider konnten wir nicht feststellen, das es sich um ein Gewährleistungsfall handelt.
Wir haben die Ware daher ohne Anerkennung einer Rechtspflicht zur Prüfung der Garantieansprüche zum Lieferanten / Hersteller aus Kulanz weitergeleitet.

Mal sehen. Ich glaube, das gibt noch Stress.

Fun Fact: Ich habe vor einigen Tagen zum Testen meiner Backup Platte einen komplette Scan aller Sektoren durchgefüht. Da die Platten für die Dauer der Überprüfung nicht genutzt werden können logischerweise über Nacht. Und ich muss sagen – mein Biorhythmus ist mittlerweile ziemlich effizient. Nicht nur wache ich seit einer Woche grundsätzlich vormittags auf, an dem Tag bin ich auch noch exakt eine Minute vor Abschluss der Überprüfung aufgewacht. Praktisch.

Rebel 9. Was ein Tower.

Season Finale!
Früher habe ich Serienjunkies immer ein wenig spöttisch betrachtet. Wie kann man nur so viel Freude an irgendeiner doofen US-Serie mit eingespielten Lachern finden? Mittlerweile verfolge ich selber aktiv How I Met Your Mother und The Big Bang Theory. Beide hatten diese Woche Finale. Zumindest für diese Staffel. How I Met Your Mother hat mich nicht vom Stuhl gehauen. Bei Big Bang Theory habe ich wie eigentlich jede Woche herzlich gelacht. Aber mir ist zumindest klar geworden, dass man Serien nicht vergleichen kann. Big Bang Theory setzt auf Comedy. Situationslacher. Hingegen hat How I Met Your Mother diese Staffel versucht, den feinen Grad zwischen Unterhaltung und tiefgreifenderen Inhalten zu finden. Nicht sonderlich erfolgreich, aber die Schreiber haben für sich hoffentlich Erkenntnisse gewonnen, die in der sechsten Staffel umsetzen werden. Aber wie dem auch sei – jeder hat auf dem Gebiet seine eigene Meinung.
Allgemein habe ich in letzter Zeit Gefallen an Serien gefunden: Mit The IT Crowd eine köstliche und erschreckend zutreffende Parodie auf die IT Abteilungen dieser Welt und mit Achtung! Streng Geheim! eine Serie aus den frühen 90ern. Ich habe sie damals immer nur zufällig beim “Durchzappen” gefunden und fand sie unglaublich toll. Jetzt habe ich geballte 17 Stunden davon, verteilt auf 12 85-minütige Folgen. Ein Muss für jeden Fan cooler 90er Kids.

The Big Bang Theory

Harmony
Der obligatorische Harmony Part. :) Ich habe in den letzten Tagen am Lizenzsystem einiges umgestellt und ein paar nervige Bugs entfernt. Sehr hilfreich war hier ein LuminaRO Spieler, der mir über mehrere Stunden Debugging per TeamViewer ermöglicht hat. Anderenfalls hätte das Fixen des Bugs sicherlich eine ganze Weile länger gedauert. Insgesamt steht ein neuer Debugging Ansatz aber noch immer recht weit oben auf der Roadmap. Ein Projekt wie Harmony zu debuggen gestaltet sich sonst als absoluter Albtraum.
Robin aka Zungarius hat sich weiterhin bereit erklärt ein kleines Design für meine Infopage vorzubereiten. Die innovative Domain harmonize.it ist ja bereits registriert… :)

Grand Prix d’Eurovision de la Chanson
Eurovision Song Contest
Deutschland hat gewonnen!!!11 Ich bin so unglaublich glücklich!!!1111einseinself
No, srsly. Wie sonst auch habe ich mir gestern Abend die Punktvergabe des Eurovision Song Contest angesehen. Ich gönne es Lena. Sie wirkte einfach … natürlicher als die anderen Teilnehmer. Und mit Mezzo Mix kann man eh nichts falsch machen.
Ich weiß nicht mehr genau wann und vom der Kommentar kam, aber “sie hat da einfach mal Party mit der Masse gemacht” trifft es denke ich. Meiner Meinung nach auf jeden Fall ein verdienter Sieg. :)

Mh. Das ist jetzt doch länger als erwartet geworden…

Geschafft! – Rückblick und Ausblick auf die Harmony Entwicklung

Mai 22nd, 2010 by Sirius_White

Harmony 3.1 ist fertig!

“Ich werde im Laufe des heutigen Tages das 3.1 Release Package fertig machen”
Sirius_White, 07.05.2010

Zugegeben, der “heutige Tag” ist es nicht mehr ganz geworden. Aber es wurde immerhin kein Duke Nukem Forever! :)

Vor 2 Tagen sind die vermeintlich letzten Zeilen für 3.1 fertig geworden und Zephyrus hat sein lang ersehntes Update erhalten. 2 Stunden später war dann auch ein ekelhafter Race-Condition-Bug behoben und nach den tatsächlich letzten Zeilen der 3.1 Branch als abgeschlossen markiert. Ursprünglich war der Release für Ende März angesetzt, aber durch die “Verspätung” sind immerhin zahlreiche neue Features eingeflossen, die eigentlich erst für 3.2 geplant waren. Ich kann mittlerweile denke ich mit Fug und Recht behaupten, dass in Punkto Sicherheit die aktuelle Harmony Version allen mir bekannten Anti-Bot Systemen ebenbürtig bis überlegen ist. Aber das kann ja jeder sagen, also bitte reverst Harmony – ich lege Wert auf Feedback! ;)

Für die kommenden Versionen ist bereits einiges geplant. Die oft gewünschte GRF Protection wird mit 3.2 eingebaut werden. Die relevanten Funktionen sind bereits seit Monaten vorhanden, ich muss das Interface dafür nur etwas benutzerfreundlicher gestalten. Ich setze hierbei auf verschlüsselte Dateien innerhalb der GRF, um eine größtmögliche Kompatibilität mit vorhandenen Patchern zu gewährleisten. Aber mehr dazu wenn es soweit ist. :)
Auf lange Sicht steht vor allem ein Punkt im Vordergrund: Das Öffnen der Harmony Plattform für außenstehende Entwickler. Das bezieht sich einerseits natürlich auf den Window Manager (RO Interface mit Lua erweitern), aber auf das komplette Harmony Framework ansich. Durch den modularen Aufbau sollte es möglich sein, ausgewählten Entwicklern eine Harmony SDK zur Verfügung zu stellen und somit die Entwicklung neuer Client Erweiterungen zu fördern, ohne dabei die Sicherheit des Systems zu beeinträchtigen.
Aber ich will an dieser Stelle nicht zu viel vorweg nehmen. Kommt Zeit, kommt Harmony 3.2. :)

Mein Ruf nach gelangweilten Grafikern hatte übrigens Erfolg!
Beginnend mit 3.2 wird Harmony endlich einen kleinen Splash Screen haben, auf den ich dank grafischer Omni-Inkompetenz bisher leider verzichten musste. Danke an dieser Stelle an Argon!

Neulich beim Harmony coden…

Mai 9th, 2010 by Sirius_White
Perfect Harmony!

Na dann kann ja nichts mehr schief gehen!

Harmony – der Name ist Programm!

Mai 7th, 2010 by LightFighter

… oder auch nicht.

Ich habe mich vor ein paar Tagen mal wieder dazu bewegt, mich mit Harmony zu beschäftigen. Um genau zu sein, habe ich am Window Manager gearbeitet. Das, was ich während dieser Zeit allerdings empfunden habe, war alles andere als “Harmonie”. Ich würde die Zeit eher als anstrengend, nervenaufreibend oder “OMG Warum funktioniert das nicht?!” bezeichnen..

Um diesem Artikel mal die Pointe vorwegzunehmen: ich habe es dennoch geschafft, ein bisschen was auf die Reihe zu kriegen. Daniel hat schließlich einige Vorarbeit geleistet und ich konnte am Anfang ohne viel Zeit- und Arbeitsaufwand ein total unschuldig wirkendes und leeres Custom Window bewundern: [Oder auch nicht - wegen kleinen PC/Mac Migrationsproblemen, ist der Screen leider abhanden gekommen. Ich werd ihn schnellstmöglich reproduzieren, sorry.]

Nachdem die erste Euphorie verflogen war, ging dann aber auch schon der Horror los. Ich war so naiv zu denken, dass mein größtes Problem das Durcharbeiten und Verstehen des bestehenden Harmony Codes sein würde. Doch als dies mehr oder weniger hinter mir lag, schien dennoch nichts zu funktionieren. Egal, was ich versuchte, früher oder später crashte mir der Client gnadenlos weg – ich hatte übrigens versucht, einen stinknormalen ImageButton auf das Formular zu klatschen. Und so verging jedenfalls der erste Tag ohne wirkliche Ergebnisse, juhu.

Ich habe mich dann letztendlich dazu entschieden, den BitmapButton erstmal ruhen zu lassen. Also nahm ich mir das Element vor, welches mir am simpelsten erschien: UIStaticText. Gesagt getan, und nach einem weiteren Tag Arbeit und viel sinnbildlichem Schweiß, hatte ich doch tatsächlich einen kleinen Text auf meinem Fenster!  Das musste natürlich erstmal mit einem kleinen, bescheidenen Freudentanz gefeiert werden ^^[Und auch bei diesem Screen muss ich euch vorerst enttäuschen..]

Nachdem das erste UI Objekt funktionierte, war es nicht mehr sonderlich schwer, weitere Objekte wie zum Beispiel eine InputBox bzw EditCtrl einzubauen. Ganz so einfach – “harmonisch” – lief der Prozess leider nicht ab, da durch das Party Booking System ein paar neue Eigenschaften dazu gekommen sind. Dabei habe ich allerdings auch ein paar nützliche Features entdeckt: Wie in der Gallery zu sehen ist, kann man diese Dinger richtig schön bunt machen :P Desweiteren kann man Rahmendicke, Passwordchars und vieles mehr einstellen – ziemlich praktisch.

Soweit so gut. Was ich zu Daniels Leiden noch nicht geschafft habe ist, den Offsetgenerator dahingehend zu erweitern, dass auch die ganzen WindowManager Offsets für die verschiedenen Clients generiert werden. Momentan läuft der WindowManager leider nur auf einer einzigen Exe; ich war bisher einfach zu faul, mich mit dem Offsetgenerator auseinander zusetzen, geschweigedenn, mir irgendwelche Suchmuster zu überlegen. Für ein Release ist das Modul sowieso noch viel zu unausgereift.

Wer sich jetzt fragt, warum ich das Modul überhaupt in Angriff genommen habe, wenn ich doch so faul bin, der bekomme jetzt einen Keks – gute Frage. Mein ursprünglicher Beweggrund ist das “Chains Of War” Projekt (WoW Mod für RO) von Everade, bei dem ich mitwirke – soviel Eigenwerbung sei mir gestattet. Everade bat mich nämlich, die Charaktererstellung so zu erweitern, dass der Spieler auch eine Rasse wählen kann. Sein Vorschlag war, die Charerstellung komplett aufs ControlPanel der Webseite zu verlagern, was ich allerdings für sehr unschön finde… Sobald das einigermaßen läuft, werde ich hier wahrscheinlich noch ein paar Screenshots posten.

Bis dahin, haltet die Ohren steif und bleibt so RO-fanatisch wie die ganzen Freaks auf diesem Blog,

Lighto.

Warum ich nicht poste!

Mai 7th, 2010 by Sirius_White

Zugegeben, ich war schreibfaul. Aber abgesehen davon waren die letzten Wochen hauptsächlich durch Abiturprüfungen sowie vorausgehende und anschließende Feiern geprägt. Mitte April hatte ich meine letzte Schulwoche, in der letzten Aprilwoche dann meine drei schriftlichen Prüfungen (Mathe, Englisch, Info) und heute die abschließende, mündliche Prüfung in Geschichte. Und abgesehen von der Tatsache, dass ich um 7.30 Uhr (!) in der Schule sein musste, lief auch alles ganz gut. :)

Also wie gesagt. Ich habe die vergangenen Wochen zum intensiven Lernen genutzt. Zumindest … größtenteils. Für die drei schriftlichen Prüfungen mindestens eine Stunde.

Okay, hier meine tatsächlichen Beschäftigungen:

Assassins Creed 2

Nachdem ich den ersten Teil nur auf der Xbox bei Freunden angespielt hatte, waren meine Erwartungen an den zweiten Teil der Reihe nicht sonderlich hoch. Trotz des neuen Ubisoft DRM Systems musste ich mir das Ganze aber einmal anschauen.
Seit meiner Point&Click-Adventure Phase Ende letzten Jahres (Geheimakte Tunguska bei der Fraunhofer Talent School!) habe ich eigentlich gar nichts mehr gespielt. Von daher ist es umso bemerkenswerter, wie schnell mich der Assassins Creed Sog gefasst hat. Die Story ist zwar noch immer etwas eintönig nach dem Motto “Na, wer ist der nächste Verräter?”, aber die Entwickler haben sich sichtlich Mühe gegeben, die Missionen abwechslungsreich zu gestalten. Über das nächtliche Venedig zu fliegen oder Leonardo da Vinci in einer wilden Kutschenverfolgung zu retten macht schon Spaß! :)

ROorg

Beim ROorg Projekt gab es in letzter Zeit einige Umplanungen, im Laufe des Tages werden wir auch noch das Press Release fertig machen. Da wir nun endgültig auf die Entwicklung eines eigenen Clients umgestiegen sind, wurde die Entwicklungszeit etwas verlängert. Aber mehr dazu in nächster Zeit auf der Projektseite. Es bleibt spannend!

Harmony
Fortschritt. Im Zuge des 3.1 Updates haben mehrere Designänderungen Einzug gehalten. Nebenbei sind einige neue Features dazu gekommen und alte wurden verbessert. Sprich: Ich werde im Laufe des heutigen Tages das 3.1 Release Package fertig machen und dann bekommt Zephyrus endlich seine neue Version.
Timo hat offenbar noch einen Artikel über seine Arbeit am Window Manager im Arbeit, ich werde ihn gleich mal anhauen, den fertig zu machen. Klick mich
Ansonsten wird es zu Harmony in den nächsten Tagen noch einmal eine Informationsseite oder etwas in der Richtung geben. So wirklich wissen ja die meisten noch immer nicht, was Harmony überhaupt ist.
Apropos: Ist irgendein Grafiker da draußen gelangweilt und möchte mir ein kleines Harmony Logo machen? ._.

Warum ich nicht antworte

März 30th, 2010 by Sirius_White

Es soll Situationen geben, in denen man mich nicht erreicht. In jüngster Zeit höre ich immer öfter von Betroffenen, dass sie mich im MSN und ICQ angeschrieben hätten, ohne eine Antwort zu bekommen. Sogar über Skype angerufen haben sie – und trotzdem kam keine Antwort! Seltsam…
Gehen wir das Problem einmal ganz simpel an: Um auf Textnachrichten erfolgreich zu antworten, müssen folgende Bedingungen erfüllt sein:

  • Die eingehende Nachricht muss bei meinem Messenger ankommen
  • Ich muss dies realisieren
  • Ich muss mich dazu entscheiden, darauf zu reagieren
  • Die Antwort muss ihren Weg zurück finden

Den ersten und letzten Punkt können wir in Zeiten des TCP Protokolls vernachlässigen. Wenn mein Rechner ACK sagt, dann ist ACK. FIN.

1. Realisierung der eingehenden Nachricht
Problemquelle: Ich bin nicht immer am Rechner!
Mein Rechner ist in der Regel durchgehend online. Dies hat den simplen Grund, dass er seit einiger Zeit den alten Linux Fileserver abgelöst hat und somit als Storage für dem gesamten Haushalt dient – welcher nicht nur aus mir besteht. Manchmal mache ich MSN und ICQ aus, aber normalerweise bleiben beide Programme einfach geöffnet und empfangsbereit. Heißt: Wenn ich im MSN online bin, heißt das noch lange nicht, dass ich auch wirklich online und anwesend bin. Wenn ich wieder da bin, werde ich wichtige Nachrichten schon beantworten:

2. Reaktion auf eigehende Nachricht
Problemquelle: Ich bin nicht gewillt, auf jede Nachricht sofort zu antworten.
Wer mich im MSN oder ICQ finden will, der wird dies recht schnell schaffen. Wer einen Grund hat mit mir zu reden, darf und soll das bitte auch tun.
Die meisten Leute kontaktieren mich aufgrund von eAthena oder RO-Client bezüglichen Fragen. Sofern es mir möglich ist helfe ich gerne bei Problemen, die man nicht binnen 5 Minuten im eAthena Forum lösen kann. Aber wenn jemand bei den einfachsten Dingen scheitert habe ich auf Dauer auch keine Lust, immer wieder beim Urschleim anzufangen. Wer das nicht akzeptiert, wird auch keine Antwort bekommen.

Doch die wohl beliebteste Methode, keine Antwort zu erhalten: Alle 10 Minuten nachfragen.
Niemand leistet hauptberuflich MSN Support für ein GPL Projekt. Und dementsprechend kann auch niemand gezwungen werden, irgendjemandem zu antworten. Es ist nicht die feine englische Art, aber wenn jemand nicht akzeptieren will, dass man gerade keine Zeit oder Lust hat, sich mit etwas zu beschäftigen, dann muss er damit leben, ignoriert zu werden.
Mittlerweile ist diese Community an einem Zustand angelangt, an dem man öffentlich nichts mehr in Aussicht stellen darf. Denn es endet zwangsläufig darin, dass man die Hälfte seiner Zeit damit beschäftigt ist, irgendwelchen Leuten klar zu machen, dass man sich nicht 24 Stunden am Tag mit ihren Problemen befassen kann und möchte.
Je penetranter man versucht eine Antwort zu bekommen, desto höher ist die Wahrscheinlichkeit im Endeffekt auf der Blockliste zu landen oder einen Blogpost wie diesen zu provozieren und danach auf der Blockliste zu landen. Im Endeffekt hat niemand gewonnen und jeder ein wenig zu viele Nerven verloren.

Was diesen Blogpost inspiriert hat? Folgende Unterhaltung “mit” einem Mitglied der deutschen eAthena Szene. Wenn ich nach Hause komme und einen derartigen Spamblock sehe, werde ich ganz bestimmt nicht mehr antworten:

[18:21] huhu
[19:05] biste nun da?
[19:05] oder noch nicht
[19:47] und wer da?
[20:18] da?
[20:48] da?
[21:26] biste nun da?
[21:52] da?
[22:25] da?
[22:57] da?’
[23:01] keiner schade =(
[23:08] wo isser denn eingepennt
[23:18] meld dich bitte egal wie spät wir haben echt nen problem und muss das dringend lösne
[23:53] ich hoffe du kommst heute nich >.<
[23:53] noch
[00:17] da?
[00:42] nun da?
[01:00] jetzt da?
[01:19] da?
[11:24] huhu
[12:30] nun jemand da?
[22:25] huhu
[22:26] da?
[01:43] huhu
[10:49] huhu
[10:53] jemand da?
[12:12] huhu
[12:16] hallii
[20:10] huhu
[22:44] huhu
[23:12] da?
[00:29] da?

Party plzzzz!

März 26th, 2010 by LightFighter

… oder: “Verschwinde aus meinem Kopf, Gravity!”

Ich bin fast aus allen Wolken gefallen, als Yommy (yomanda) mir folgenden Link über Gravitys neues Party Booking & Recruiting System präsentierte: Click meh.

Meine Antwort war folgende:

DAMNIT

I WANTED TO DO THAT

FUCK YOU GRAVITY

Bedarf wahrscheinlich keiner Übersetzung. Der Grund für meinen leicht ausfallenden Ton war, dass ich seit mehreren Wochen und Monaten die Idee gehegt hatte, irgendwann ein solches System mit Harmony zu realisieren. Das Timing von Gravity ist natürlich perfekt, denn Harmony ist gerade jetzt in einem Stadium, in dem ich durchaus hätte anfangen können, die ersten Windows zu entwerfen und das Backend zu programmieren. Aber nein, Gravity war mal wieder schneller! Aber mir macht das natürlich nichts aus, ich bin ja ein friedliches, und zartbesaitetes Wesen …..

Ich habe mich dann die letzten Tage daran gemacht, das System mal auseinander zu nehmen – was erstmal gar nicht so einfach war, da sich bisher noch niemand bequemt hat, das Interface zu übersetzen. Also mal schnell die aktuelle msgstringtable generiert, Google Translate drüber gejagt und nachgebessert. Nach getaner Arbeite öffne ich also meinen Client und freue mich auf ein nicht-koreanisches Booking Interface und – werde bitter enttäuscht. Es wurden vielleicht 2 oder 3 “Stringlein” genutzt, der Rest war wie vorher. Super.

Ein kurzer Blick in den ASM Code lässt böses erahnen: Es reicht Gravity anscheinend nicht, mir meine Idee zu klauen – nein! Irgendein Gravity Praktikant hat es anscheinend als unheimlich witzig empfunden, 90% der benutzten Strings hardcoded im Client zu verankern. Sicher, natürlich. Nachdem ich dann alle Strings per Hand im Hexeditor gesucht und übersetzt hatte, konnte ich dann tatsächlich mit einem englischen Booking Interface arbeiten. Bis auf ein paar Schönheitsfehler machte das Interface erstmal einen gar nicht mal so schlechten Eindruck:

Als ich dann anfing, die Packets zusammenzusuchen und zu analysieren, ist mir das wahrscheinlich beste Feature des ganzen Systems in die Hände gefallen: Die LSD Videos! Diese “Videos”, eher Foto Slideshows, bekommt man zu sehen, sobald man ein Party Recruit aufmacht, und auf antworten wartet. Sechs verschiedene Slideshows zum Thema Party, die wirklich nur in Verbindung mit Lysergsäurediethylamid entstanden sein können – herrlich!

Mein anfängliches Packet-Abenteuer ist dann im Laufe des Tages ausgeartet und schließlich haben White und ich alle möglichen neuen RE Packets im Client auseinander genommen und dokumentiert, die eAthena noch nicht unterstützt und haben sie dann im eA Forum gepostet. Sind ein paar wirklich interessante – und auch kuriose – Packets dabei gewesen, aber hat definitiv viel Spaß gemacht :)

Ach, und ja, ich blogge hier jetzt neuerdings mit :P

See ya,

Lighty

Unde venis?

März 22nd, 2010 by Sirius_White

Modulare Programme haben in der Regel zentrale Loggingfunktionen. Nun lässt sich zwar alles wunderschon loggen, doch die wichtigste Information fehlt in der Regel – welches Plugin hat diesen Logeintrag erzeugt?

Ich bin auf die Problematik gestoßen, als mich Timo gefragt hat, wie man herausfinden könnte, von welcher DLL ein Call kommt. Da ich zu dem Zeitpunkt selber gerade dabei war, die Modulfunktionen von Harmony zu entwerfen, habe ich mir darüber ein wenig Gedanken gemacht.

Man kann man natürlich den Log Aufruf mit einem weiteren Parameter ausstatten, um den Pluginnamen anzugeben. Simpel und funktioniert natürlich auch. Aber es geht noch eleganter!

Einige Theorie vorweg:
Um herauszufinden von welcher Dll ein Call kommt benötigt man die Speicheradresse, von der der Aufruf kommt. Wenn man dann noch eine Liste aller geladenen Module hat, lässt sich der Name relativ leicht herausfinden. Die Frage ist daher: Wie kommt man an die Adresse des “Aufrufers”?
Windows (im 32-Bit Modus) und somit auch Ragnarok basieren auf der x86 Prozessorarchitektur. Auch wenn man ein 64-Bit Windows verwendet, denn dann wird über WOW64 eine 32 Umgebung “emuliert”.
Ein Funktionsaufruf wird über den call Befehl ausgeführt, ein Rücksprung über ret. Ein call schreibt die Speicheradresse des Befehls nach dem Aufruf auf den Stack und springt zur Funktionsadresse. Ein ret holt sich den obersten Wert vom Stack und springt dorthin zurück. Soweit ganz simpel.
Lokale Variablen innerhalb der Funktion werden ebenfalls über den Stack realisiert. Man kann folglich nicht davon ausgehen, dass das oberste Element die Rücksprungadresse ist und braucht eine Möglichkeit, diese von jeder Position aus zu finden. An dieser Stelle kommt das ebp Register ins Spiel: Das ebp verweist auf die Stackposition, an der sich die Funktion am Anfang befunden hat. Über den Wert von ebp sollte man daher doch relativ leicht an die Rücksprungadresse kommen…?
Mir war der Aufbau eines C(++) Calls bereits bekannt, aber solche Informationen lassen sich auch über Wikipedia oder normale Google Recherche herausfinden.

Testcode:

Die Ausgabe sieht schonmal vielversprechend aus. Die Rücksprungadressen liegen im Bereich der main() Funktion. Dass sich die Adressen immer ändern hängt mit der Address Space Layout Randomization (ASLR) zusammen, wodurch die Basisadresse des Programms sich bei jedem Start verändert. Nichtsdestotrotz haben wir nun eine gültige Rücksprungadresse!

Nun müssen wir dieser Basisadresse den Namen eines Plugins zuordnen. In der Regel sind Plugins eigenständige Dll Dateien. Über die Compilerdokumentation findet man relativ schnell heraus, dass Dlls im Speicher auf 64Kb Adressen alignt sind – die Basisadresse also ein Vielfaches von 64Kb ist.
Eine 32 Bit Applikation kann maximal 4Gb Speicher adressieren. Normalerweise stehen dem Programm nur 2Gb zur Verfügung, da 2Gb für den Kernel reserviert sind. Allerdings gibt es die /3GB Option und unter 64-Bit Windows sieht das Ganze wieder anders aus. Wir müssen also davon ausgehen, dass wir 4Gb / 64Kb = 65536 mögliche Dll Basisadressen haben. Wenn wir im Programm ein Array verwenden, wo für jede mögliche Basisadresse ein Pointer auf den Namen hinterlegt ist, benötigt dieses array 64Kb * 32 Bit = 256 Kb. Durchaus vertretbar.

Problematisch könnte es nun werden, wenn eine Dll größer als 64Kb ist, also effektiv mehrere Basisadressen einnehmen würde. Um diesen Fall abzuhandeln muss beim Laden der Dll aus dem PE Header die SizeOfImage ausgelesen werden:

The size (in bytes) of the image, including all headers, as the image is loaded in memory.

Mit dieser Information kann man einfach ausrechnen wie viele Basisadressen belegt werden.

Wir sind also in der Lage die Rücksprungadresse einer Funktion zu ermitteln und haben ein Array in dem die Namen der Dlls hinterlegt sind. Daraus könnte dann beispielsweise das folgende Testprogramm resultieren: Klick mich.

Ziel erreicht!
Ein paar Tage nach der Entstehung dieser Zeilen bin ich über die MSDN Library auf eine sehr interessante Funktion des Microsoft Compilers gestoßen: _ReturnAddress(). Damit hätte ich mir den ganzen Aufwand sparen können – aber so ist immerhin dieser Artikel herausgekommen, der hoffentlich ein paar Anregegungen geben konnte. :)

Übrigens:
_ReturnAddress:

Meine Version:

Microsoft hat wohl den selben Ansatz verfolgt ;)