Seite 1 von 2 12 LetzteLetzte
Ergebnis 1 bis 10 von 11
  1. #1
    Anfänger Avatar von Cardano
    Registriert seit
    06.07.2010
    Beiträge
    17

    Beitrag [PE] Erstellen von Codecaves

    Hi Leute, mein erster Post und dann gleich sowas
    Und zwar hab ich ein kleines Problem bei meinem ersten C++ Projekt. Ich arbeite daran mich ein bisschen mit dem PE-Dateiformat auseinander zu setzen. Dabei hab ich natürlich einfache Dinge wie das allgemeine Zurechtfinden im Format usw. schon hinter mir. Aktuell versuch ich mich daran Codecaves zu ERZEUGEN. Also nicht bereits vorhandene auszunutzen. Hierbei mache ich folgendes:

    Ich suche mir ein RawOffset innerhalb der Datei, erstelle dort ein Codecave (Nullbytemuster) einer variablen Größe.

    Sagen wir ich erzeuge beim OEP ein Codecave der Größe 0x10, also 16Byte.
    Der OEP meiner Datei (weiter unten) liegt bei der RVA 0x000111BE, das entspricht dem RawOffset 0x5AE. Und am Ende der Section ist ein Codecave mit einer Größe von 428 Byte. Dann wird sozusagen ab dem OEP alle Bytes um 0x10 in dieses Codecave am Ende der Section verschoben. Die restlichen Sections bleiben unberührt. Dies ist jetzt nur der einfachste Fall den ich behandle. Aber da ich im Moment nur so arbeite, dass dieser eintrifft und bei mir Fehler aufkommen, wollet ich hier um Hilfe fragen.

    Folgendes mache ich noch vor dem eben beschriebenen:
    Ich bestimme das Interval der betroffenen Bytes, also in diesem Fall von dem RawOffset des OEP bis zum virtuellen Ende der Section, also
    von OEP bis (HeaderDerSection->PointerToRawData + HeaderDerSection->Misc.VirtualSize)

    Dann gucke ich mir alle Relocations im RelocationDirectory an und vergleiche zum einen ob die RawOffsets auf welche sie zeigen betroffen sind und zum anderen ob die Pointer die dort liegen in das betroffene Interval zeigen. Beide Pointer (RVA's) werden jenachdem mit 0x10 addiert und wieder gespeichert.

    Nachdem ich die Relocations abgearbeitet habe, versetze ich den OEP um 0x10 (im Mom. möchte ich noch keinen Crypter erstellen sondern einfach nur diese Funktion zum Laufen kriegen, also teste ich erstmal ob das Programm noch läuft) und dann setze ich die neuen Daten des SectionHeaders so, dass er wieder UpToDate ist was Virtual und RawSize angeht.

    Das sind zumindest alle Schritte die ich glaube machen zu müssen (ich code erst seit 5 Tagen in C++ und seit 6 Tagen beschäftige ich mich erst mit dem PE-Format)

    Hier mal ein kleiner PrintOut meiner Rederections die ich setze aus meiner Konsole:

    C:\_projects\justcrypt\Debug>J - Anonymous - Jm0R0CnN - Pastebin.com
    (Zur Erklärung: In den ersten Zeilen lass ich mir Caves am Ende von Sections ausgeben, dann im Großen bereich lass ich mir die Relocations ausgeben, hierbei gilt das Muster
    Reloc RelocationblockID - RelocationBlockEntryID : Old: <Altes Word der Relocation>, New: <ggf. neuer Wert> - RawOffset: <wohin die low 12 bit + die RVA des RelocBlocks als RawOffset zeigen> , Value(RO): <der Wert der am RawOffset liegt umgewandelt in ein RawOffset>

    Hier der Code den ich in kompilierter Form verarbeite:
    Code:
    /*----------------------------------------------------------
        HelloMsg.cpp - Gibt den Text "Hello World" in einem
        Meldungsfenster aus
      ----------------------------------------------------------*/
    
    #include <Windows.h>
    
    int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
                       PSTR szCmdLine, int iCmdShow)
    {
        MessageBox(NULL, TEXT("Hello World"), TEXT("HelloMsg"), 0);
    
        return 0;
    }
    Und hier die kompilierte Version (hello_world.exe) und die Ausgabe meines Programmes (hello_world_modified.exe)
    http://rapidshare.com/files/406351136/helloworld.rar
    Wenn ihr das ganze in einem PE-Editor öffnet, werdet ihr bspw. sehen, dass zb der OEP wirklich um 0x10 versetzt wurde. Da ich leider überhaupt keine Erfahrung mit Debuggern habe bin ich auf eure Hilfe angewiesen. Hab ich was vergessen oder wurden irgendwelche Werte falsch gesetzt ?

    Vielen Dank schonmal, Cardano
    Geändert von Cardano (11.07.2010 um 15:29 Uhr)


  2. Folgende Benutzer haben sich für diesen Beitrag bedankt:

    Mofo (11.07.2010)

  3. #2
    BackNine Wurm Avatar von Mofo
    Registriert seit
    29.11.2008
    Beiträge
    312

    Standard

    Sehr interessant was du vorhast, die Idee ist durchaus zu gebrauchen
    Ich versuche das auch mal und schau ob ich den Fehler finde, ich bin noch sehr verschlafen..
    Wenn dann werde ichs editieren

    /edit :Ok die Idee ist kaum umzusetzen vor allem nicht mit meinen Asm-Kenntissen :/ , ich denke ich bleibe weiterhin beim ausnutzen vorhandener Caves , oder schaffe mir zusätzlichen Platz am Ende der PE
    Geändert von Mofo (11.07.2010 um 16:59 Uhr)




  4. #3
    Anfänger Avatar von Cardano
    Registriert seit
    06.07.2010
    Beiträge
    17

    Standard

    Vielen Dank schonmal =)
    Ich würde mich am Liebsten selber daran machen den Fehler zu beheben. Nur leider hab ich bisher noch gar nicht mit Debuggern gearbeitet. Und wenn man die hello_world_modified herunterlädt dann sieht man, dass sie abstürzt ohne einen Fehler auszugeben. Es wäre echt schon hilfreich wenn mir jemand sagen könnte warum sich Datei abschießt, bzw. wobei. Schafft der Loader die Datei zu laden und sie verendet erst beim Ausführen von Code am neu gesetzte OEP oder verendet der Loader schon bei irgendetwas ? Wie zum Beispiel an dem Relocations oder sonst irgendwas.

    Hab ich vielleicht sonst noch etwas vergessen ?
    Wie gesagt es wurden folgende Werte verändert:
    Pointer in das betroffene Interval, Addresse des OEPs und RawSize und VirtualSize der Section im SectionHeader
    Geändert von Cardano (11.07.2010 um 15:48 Uhr)

  5. #4
    I'm in ur VM. Avatar von l0dsb
    Registriert seit
    23.07.2007
    Beiträge
    1.038

    Standard

    Eins vorweg: Wenn du dich bereits mit Themen wie PE-Modifikation beschäftigen willst, ist der Umgang mit einem Debugger auf Binary-Basis mehr oder weniger ein "Muss". Lena151 hilft da gerne weiter, was OllyDbg betrifft.

    Du verschiebst nicht alle Relocations richtig. Am OEP befindet sich bereits ein JMP, der über deine Codecave springt (Ziel außerhalb des Intervalls, wenn ich deine Beschreibung oben richtig verstanden habe) und somit 0x10 Byte unter seinem eigentlichen Ziel landet.

    Entwickelst du das System nur zum Spaß oder was möchtest du damit erreichen? Unter Umständen gibt es eine elegantere Möglichkeit, das ähnlich umzusetzen.

    Muss die Cave mitten im Code liegen (erhöhter Aufwand, wenn sich irgendwann noch die Boundaries anderer Sections verschieben, da diese auch angepasst werden müssten) oder was spricht gegen Caves am Ende einer Section, Backup des OEPs und Cave in der ersten Section, Hinzufügen einer Section, ...
    I can haz RCE?

  6. Folgende Benutzer haben sich für diesen Beitrag bedankt:

    Mofo (11.07.2010)

  7. #5
    OpCodeKiddy Avatar von EBFE
    Registriert seit
    30.03.2009
    Beiträge
    442

    Standard

    Verstehe ich es richtig: du "schiebst" 0x10 Bytes "mittenrein" in den Code und passt dann diese über Relocations an? Dann sehe ich auf Anhieb folgende Probleme: zum einen sind Relocations bei Exen eher "optional" und werden nicht von allen Compilern/Linkern produziert.
    Zum anderen: Relocations an sich decken den "Anpassbedarf" bei weitem nicht ab. Denn viele JMPs und CALLs (auf Maschinencodelevel) sind relativ - also in der Form "Springe/Calle zu der Stelle: _aktuelle_position + XYZ Bytes". Und diese werden keineswegs von Relocations irgendwie korriegiert (denn aufgrund ihrer "Relativität" laufen sie eher mit jeder ImageBase). D.h dass alle relativen JMPs und CALLs in und aus dem "verschobenen" Bereich dann dementsprechend 0x10 Bytes daneben gehen.
    Geändert von EBFE (11.07.2010 um 16:22 Uhr)
    TrueCrypt/RAR/Zip Passwort vergessen und das Bruten dauert ewig? Oder brauchst du fein abgestimmte Wortlisten? Hilf dir selbst mit WLML - Word List Markup Language
    Gib Stoned/Mebroot/Sinowal und anderen Bootkits keine Chance: Anti Bootkit v 0.8.5

  8. #6
    Anfänger Avatar von Cardano
    Registriert seit
    06.07.2010
    Beiträge
    17

    Standard

    Zitat Zitat von l0dsb Beitrag anzeigen
    Muss die Cave mitten im Code liegen (erhöhter Aufwand, wenn sich irgendwann noch die Boundaries anderer Sections verschieben, da diese auch angepasst werden müssten) oder was spricht gegen Caves am Ende einer Section, Backup des OEPs und Cave in der ersten Section, Hinzufügen einer Section, ...
    Es MUSS nirgendwo liegen :p Ich schreibe zum Spaß, um mich an dem Umgang mit C++ zu gewöhnen (ich code seit einem halben Jahr mit PHP und fang jetzt mal mit C++ an) an diesem Projekt. Die von dir beschriebenen Fälle decke ich ebenfalls ab. Ich versuche das ganze so komplett wie möglich zu gestalten mit dem Endziel vielleicht IRGENDWANN mal damit einen Crypter zu basteln. Ich versuche mich mit jedem einzelnen Teil der PE Spezifikation auseinander zu setzen um so eine lib zu entwickeln mit der ich einfach PE Datein modifizieren, kombinieren und neu zusammensetzen kann.

    Zum 2. Abschnitt:
    Könntest du genauer beschreiben was du meinst?
    Achso sry, die oben im Text beschriebenen angaben sind zu einer anderen Datei =(, Hier nochmal ein Print in dem ich mehr Informationen gleich ausgeben lasse, eben hatte ich einige deaktiviert, so kriegt ihr gleich Informationen zur richtigen Datei hello_word.exe):
    Es passen 8 SecionHeader in da - Anonymous - DYt7kwdc - Pastebin.com

    Wenn du hier auch einen Fehler findest, sag bitte die RelocBlock ID und die RelocBlockEntry ID die du meintest.

    Vielen Dank schonmal für die Mühe

    btw.: Wer ist Lena151?

    EDIT: Ah danke EBFE. Heißt das ich habe mit dem Unterfangen schon vorloren ? Oder kann man es schaffen diese JMP's aufzuspüren und ebenfalls anzupassen ?
    Geändert von Cardano (11.07.2010 um 16:26 Uhr)

  9. #7
    I'm in ur VM. Avatar von l0dsb
    Registriert seit
    23.07.2007
    Beiträge
    1.038

    Standard

    Wenn sich die Boundaries verschieben, musst du dich zwangsweise mit jedem Teil der Spezifikation auseinandersetzen, da du dann z. B. auch das Resource-Directory relocaten musst.

    Lena151 hat eine Einführung in die Verwendung von OllyDbg gegeben (zum Reverse Engineering). Nichtsdestotrotz interessant für dich, wobei du dir noch Assembler ansehen solltest.

    EBFE hat natürlich recht im Bezug auf die short jumps. Diese hundertprozentig aufzuspüren und anzupassen halte ich für utopisch (oder schlichtweg für zu viel Mehraufwand in Anbetracht der zu erledigenden Aufgabe).

    Um Daten an eine PE-Datei anzuhängen, wird üblicherweise die Resource-Section verwendet (auch prima für Code zu verwenden, vgl. 29a eZine), die letzte Section erweitert oder eine neue Section eingefügt.

    Damit der Entrypoint nicht in der letzten Section liegt (heuristic detection), können ein paar Byte des OEPs in die letzte Section verschoben werden und ein Sprung (nicht wortwörtlich, aber funktional) zum Code in der letzten Section ausgeführt werden (vgl. ASProtect).
    I can haz RCE?

  10. #8
    OpCodeKiddy Avatar von EBFE
    Registriert seit
    30.03.2009
    Beiträge
    442

    Standard

    EDIT: Ah danke EBFE. Heißt das ich habe mit dem Unterfangen schon vorloren ? Oder kann man es schaffen diese JMP's aufzuspüren und ebenfalls anzupassen ?
    Zuerst müssten wir sichergehen, dass wir nicht aneinander vorbeireden
    D.h ich denke, dass du folgendes möchtest:
    Code:
    040 1000 code
    040 1002 code
    <--- hier wird eine 16 Byte Codecave eingeschleußt
    040 1003 + 0x16 nun ist der restliche Code quasi um 16 Bytes verschoben
    Um richtig zuverlässig zu arbeiten, müsste dein Code mit einem Disassembler durch den kompletten Code durchgehen und alle CALLS und JMPs in den nun verschobenen Bereich um die Intervallänge korrigieren. Dasselbe gilt für CALLs/JMPs aus diesem Bereich in den "restlichen" Code (allerdings nicht für Sprünge innerhalb des Bereichs). Wie schwer es ist, wirklich zuverlässig zu disassemblieren, braucht man glaub ich nicht zu erwähnen. Obwohl die üblichen Disassemblerengines in 90% aller Fälle sehr brauchbare Ergebnisse liefern sollten. Die Frage ist, ob du solche Komplexität möchtest? Denn letzendlich ist es 100 mal einfacher, die Codecave am Ende der Seciton einzufügen, in dem man den Unterschied zwischen RawSize und VirtualSize sowie SectionAlignment vs. FileAlignment ausnutzt (die Sectionheader Korrektur muss ja auch bei deiner Methode erfolgen). Zudem du die "Boundarys" der nachfolgenden Sections eher nicht verschieben kannst (bei Verschiebung ergeben sich noch heftigere Probleme, als gerade mit der Codeverschiebeung )

    Edit: es sind ja nicht nur short JMPs betroffen, auch "long JMPs" + Calls sind sehr oft relativ (nur sieht/merkt man das normalerweise in OllyDbg nicht, da Olly direkt die Zieladresse anzeigt).
    Hier ein Auszug der CALC.exe ab den OEP - in den 190 Bytes sind gleich 3 relative Calls "nach Außen" drin und ein haufen Jmps.
    Geändert von EBFE (11.07.2010 um 16:56 Uhr)
    TrueCrypt/RAR/Zip Passwort vergessen und das Bruten dauert ewig? Oder brauchst du fein abgestimmte Wortlisten? Hilf dir selbst mit WLML - Word List Markup Language
    Gib Stoned/Mebroot/Sinowal und anderen Bootkits keine Chance: Anti Bootkit v 0.8.5

  11. Folgende Benutzer haben sich für diesen Beitrag bedankt:

    Mofo (11.07.2010)

  12. #9
    Anfänger Avatar von Cardano
    Registriert seit
    06.07.2010
    Beiträge
    17

    Standard

    Ich kann ja mal ein bisschen Code posten
    C++ | bool PEFile::createCodecave(__ - Anonymous - yMHiSKHw - Pastebin.com

    Wie man sieht, bin ich in der Implementierung noch nicht allzu weit. Wann immer euch ein (void) 0; begegnet habe ich noch nicht weitergemacht. Ich hatte mir für den Fall, dass das Codecave nicht groß genug ist ausgedacht, dass ich "einfach" wieder ein RELOC_INTERVAL
    Code:
    typedef struct _RELOC_INTERVAL {
        DWORD    roLowBoundary;
        DWORD    roHighBoundary;
        DWORD    dwDelta;
    } RELOC_INTERVAL;
    erzeuge mit der Größe dwDelta, welche sich wie in Zeile 22 zu sehen
    aus
    Code:
    iDeltaFollowingSections = Align(iCaveSize - ccAffectedSection->iCaveSize, this->pImageNTHeaders->OptionalHeader.FileAlignment);
    ergibt.
    Dann relocate ich wieder alles von der darauf folgenden Section bis zum Ende der letzten physischen Section
    Danach muss ich ggf. noch einige(viele) Angaben in den Datadirectorys anpassen, wie zum Einen natürlich die Addresse des RelocDirs an sich, ggf. ExportDir usw. und sofort.

    Aber dann kommen mir natürlich nun die short calls/jumps in die Quere.
    D.h., wollte ich fortfahren müsste ich mein Glück mit einer Disassemblierungsengine versuchen, die auch nur zu 90%iger Wahrscheinlichkeit mit die richtigen Befehle gibt um das Problem zu lösen, oder ?
    Geändert von Cardano (11.07.2010 um 17:05 Uhr)

  13. #10
    I'm in ur VM. Avatar von l0dsb
    Registriert seit
    23.07.2007
    Beiträge
    1.038

    Standard

    Wenn die long jumps relativ sind und der Compiler Relocations erzeugt, tut er das auch für diese. Relativ sind die ja sowieso, am Offset ändert das ja nichts (00000000 ist ja genauso ein Offset wie jeder andere auch und kann dementsprechend reloziert werden).

    edit
    Deine letzte Frage lässt sich wohl nur bejahen, wie man schon EBFE's Beitrag entnehmen kann. Relokationsinformationen für short jumps sind in der Regel (normaler Kompiliervorgang) sinnfrei, da diese ja nur direkt abhängig von der Quell- aber nicht von der Zieladresse sind. Diese müsstest du per Disassembly finden, was nicht immer zum Erfolg führen muss.
    Geändert von l0dsb (11.07.2010 um 17:13 Uhr) Grund: Cardano's Beitrag
    I can haz RCE?

Seite 1 von 2 12 LetzteLetzte

Ähnliche Themen

  1. [S] [VB6] erstellen
    Von Toxic2124 im Forum Komponenten & Source Codes
    Antworten: 8
    Letzter Beitrag: 18.12.2008, 18:18
  2. [S] tut zum Key Gen erstellen
    Von Planxty im Forum Suche Tutorials
    Antworten: 11
    Letzter Beitrag: 28.02.2008, 18:19
  3. CSS Server erstellen need help
    Von pasqualebia im Forum Games
    Antworten: 3
    Letzter Beitrag: 11.11.2007, 15:01

Stichworte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •