Format Strings
Grundinformationen
In C printf
ist eine Funktion, die verwendet werden kann, um einen String auszugeben. Der erste Parameter, den diese Funktion erwartet, ist der rohe Text mit den Formatierern. Die folgenden Parameter, die erwartet werden, sind die Werte, um die Formatierer aus dem rohen Text zu ersetzen.
Andere verwundbare Funktionen sind sprintf()
und fprintf()
.
Die Verwundbarkeit tritt auf, wenn ein Angreifertext als erstes Argument für diese Funktion verwendet wird. Der Angreifer kann eine spezielle Eingabe erstellen, die die printf-Format-String-Funktionen ausnutzt, um beliebige Daten an beliebiger Adresse (lesbar/schreibbar) zu lesen und zu schreiben. Auf diese Weise kann er beliebigen Code ausführen.
Formatierer:
Beispiele:
Verwundbares Beispiel:
Normale Verwendung:
Mit fehlenden Argumenten:
fprintf anfällig:
Zugriff auf Zeiger
Das Format %<n>$x
, wobei n
eine Zahl ist, ermöglicht es, printf anzuzeigen, dass der n-te Parameter (vom Stack) ausgewählt werden soll. Wenn Sie also den 4. Parameter vom Stack mit printf lesen möchten, könnten Sie Folgendes tun:
und du würdest vom ersten bis zum vierten Parameter lesen.
Oder du könntest Folgendes tun:
und direkt das vierte lesen.
Beachten Sie, dass der Angreifer den printf
Parameter kontrolliert, was im Grunde bedeutet, dass seine Eingabe im Stack sein wird, wenn printf
aufgerufen wird, was bedeutet, dass er spezifische Speicheradressen im Stack schreiben könnte.
Ein Angreifer, der diese Eingabe kontrolliert, wird in der Lage sein, willkürliche Adressen im Stack hinzuzufügen und printf
dazu zu bringen, auf sie zuzugreifen. Im nächsten Abschnitt wird erklärt, wie man dieses Verhalten nutzt.
Willkürliches Lesen
Es ist möglich, den Formatter %n$s
zu verwenden, um printf
die Adresse an der n Position zu entnehmen, die ihm folgt, und sie so zu drucken, als wäre es eine Zeichenkette (drucken, bis ein 0x00 gefunden wird). Wenn also die Basisadresse des Binaries 0x8048000
ist und wir wissen, dass die Benutzereingabe an der 4. Position im Stack beginnt, ist es möglich, den Anfang des Binaries mit:
Beachten Sie, dass Sie die Adresse 0x8048000 nicht am Anfang der Eingabe setzen können, da der String bei 0x00 am Ende dieser Adresse abgeschnitten wird.
Offset finden
Um den Offset zu Ihrer Eingabe zu finden, könnten Sie 4 oder 8 Bytes (0x41414141
) senden, gefolgt von %1$x
und den Wert erhöhen, bis Sie die A's
erhalten.
Last updated