Archiv verlassen und diese Seite im Standarddesign anzeigen : Stack-Buffer-Overflow
Chrisimo
27.10.2006, 16:44
Hallo Leute,
ich beschäftige mich seit kurzem mit dem Thema Stack-Buffer-Overflow und bin dabei natürlich auf verschiedene Probleme gestoßen. Mein System ist Kubuntu 6.06 (vielleicht nicht das beste Anfängersystem für diese Dinge :)).
Das 1. Problem, nämlich die ständig wechselnden Speicheradressen des Stacks habe ich schon gelöst, aber ich hänge im Moment an einem weiteren Problem fest:
int Variablen werden immer unterhalb von char Variablen auf dem Stack abgelegt (also näher zum EBP). Wenn ich nun einen Fehler in der Form
(for i=0;i<1024;i++) {
buf1[i]=buf2[i];
} (bei buf1[200] oder ähnlich)
ausnutzen will, dann überschreibe ich leider auch immer die Variable i und die Schleife wird rechtzeitig beendet. Gibt es irgendwelche Ansätze oder Lösungen für das Problem?
Gruß,
Chrisimo
Nimm halt ne andere Reihenfolge fuer die Variablen:
char leet[200];
int i;
Wenn du keine komischen Compiler-Optimisierungen angeschaltet hast, sollte das dann auch die Reihenfolge auf dem Stack sein, womit i dann nicht ueberschrieben wird.
Chrisimo
27.10.2006, 17:35
Das hab ich schon probiert. Die int's liegen immer unter den char's. Muss am compiler liegen. Kann man wahrscheinlich nix machen, was?
welchen Compiler benutzt du denn? Guck doch mal im Manual nach, vielleicht steht da ja was.
Ansonsten benutz vielleicht ein anderes programm, strcpy(bla,argv[23]) o.ae. ist IMO sinnvoller; bei deinem Beispiel kannst du aber auch einfach memcpy benutzen, das macht das selbe.
Chrisimo
27.10.2006, 18:17
mit strcpy hab ich ja schon ein exploitme gemacht. Das funktioniert ja auch. Ich wollt nur wissen, ob es trotz dieses Schutzes mit der Vaiablen-Anordnung vielleicht einen Weg gibt, die Schwachstelle auszunutzen...
Warum sollte das einen "Schutz" darstellen?
Unter der Annahme, dass buf2 user-controlled ist:
Du hast Kontrolle ueber i, also setz es auf was sinnvolles.
Chrisimo
28.10.2006, 10:03
Darauf zielte ja meine ursprüngliche Frage ab. Was denn etwas sinnvolles sein könnte.
Nochmal das Beispiel:
void function(char *buf2) {
char buf1[12];
int i;
for (i=0;i<=12;i++) {
buf1[i]=buf2[i];
}
}
Okay. Also setze ich das 13.Byte ([12]), das dann i überschreibt auf 14. Dann wird die Schleife beendet. Setze ich es auf 0 wird die Schleife wieder von Anfang an durchlaufen, allerdings wird buf1 auch wieder von Anfang an beschrieben - also eine Endlosschleife...Worauf könnte man i denn noch setzen? Entweder die Schleife wird beendet, oder sie fängt von vorne an.
Was ist denn mit dem Wert, den es normalerweise annehmen wuerde? Was wuerde dann passieren?
Chrisimo
29.10.2006, 11:56
Ich würde sagen die Schleife wird normal beendet, da i dann 12 ist??
i=0 -- buf2[0]='A' => buf1[0]='A'
i=1 -- buf2[1]='A' => buf1[1]='A'
i=2 -- buf2[2]='A' => buf1[2]='A'
i=3 -- buf2[3]='A' => buf1[3]='A'
i=4 -- buf2[4]='A' => buf1[4]='A'
i=5 -- buf2[5]='A' => buf1[5]='A'
i=6 -- buf2[6]='A' => buf1[6]='A'
i=7 -- buf2[7]='A' => buf1[7]='A'
i=8 -- buf2[8]='A' => buf1[8]='A'
i=9 -- buf2[9]='A' => buf1[9]='A'
i=10 -- buf2[10]='A' => buf1[10]='A'
i=11 -- buf2[11]='A' => buf1[11]='A'
i=12 -- buf2[12]=0x0C => i=12
Oder nicht?
Ich sehe keine Möglichkeit den Code so zu exploiten, wenn allerdings i ein char wäre oder der Array aus ints bestehen würde, könntest du mit 'nem integer overflow arbeiten, was mit 'nem i als char wohl leichter wäre als 'nem int-Array.
Ansonsten bliebe noch die theoretische Möglichkeit, dass mit i nach der Schleife weiter gearbeitet wird, ohne vorher nochmal zu prüfen was drinsteht.
Warum sollte die Schleife dann zu Ende sein? Sie ist doch erst zu Ende, wenn i==1024. Du musst nur mit den naechsten Bytes aufpassen, damit du diesen Wert nicht ueberschreitest.
Du koenntest natuerlich auch einen anderen Wert fuer i nehmen, und die 3(ich nehme mal an, x86) most significant bytes von i gar nicht anruehren.
Weitergehend:
Bei gewissen Umstaenden kannst du eventuell noch andere, lustigere sachen machen, und in anderen Speicherbereichen als dem Stack rumschreiben.
Der Code von Post #7 war gemeint. ;-)
oops, das hab ich verrafft.
Wenn da i wirklich "hinter" dem char-array steht, kann man da wirklich nichts machen, da das modifizierte i ja nicht mehr benutzt wird.
Das erste Beispiel sollte aber so funktionieren.