Frage

Dies ist ein Shellcode die Bufferover Sicherheitsanfälligkeit ausnutzt. Er setzt die setuid(0) und laicht eine Schale mit execve(). Unten ist die Art, wie ich es interpretiert haben:

xor    %ebx,%ebx       ; Xoring to make ebx value 0
lea    0x17(%ebx),%eax ; adds 23 to 0 and loads effective addr to eax. for setuid()
int    $0x80           ; interrupt
push   %ebx            ; push ebx
push   $0x68732f6e     ; push address // why this address only????
push   $0x69622f2f     ; push address // same question
mov    %esp,%ebx
push   %eax
push   %ebx
mov    %esp,%ecx
cltd                   ; mov execve sys call into al
mov    $0xb,%al
int    $0x80           ; interrupt

Kann du jemand die ganzen Schritte klar erklären?

War es hilfreich?

Lösung

int ist der Opcode für ein Software-Interrupt auslösen. Software-Interrupts werden nummeriert (0-255) und vom Kernel abgewickelt. Auf Linux-Systemen zu unterbrechen 128 (0x80) ist der herkömmliche Eingangspunkt für Systemaufrufe. Der Kernel erwartet das System Aufrufargumente in den Registern; insbesondere über das% EAX-Register identifiziert, welche Systemaufruf wir sprechen.

  1. Set% ebx auf 0
  2. Compute% ebx + 23 und das Ergebnis in% eax (der Opcode ist lea als „Last effektive Adresse“, aber nicht Speicherzugriff beteiligt ist; dies ist nur eine hinterhältige Art und Weise einen Zusatz zu machen).
  3. Systemaufruf. % EAX enthält 23, was bedeutet, daß der Systemaufruf setuid ist. Das Systemaufruf verwendet ein Argument (das Ziel UID), in% ebx gefunden werden, die zweckmäßigerweise 0 an diesem Punkt enthält (sie wurde in dem ersten Befehlssatz). Hinweis: bei der Rückkehr, sind Register unverändert, mit Ausnahme% eax, die den Rückgabewert des Systemaufrufs enthält, normalerweise 0 (wenn der Anruf war ein Erfolg)
  4. .
  5. Push% ebx auf dem Stapel (das ist immer noch 0).
  6. Drücken Sie $ 0x68732f6e auf den Stapel.
  7. Drücken Sie $ 0x69622f2f auf den Stapel. Da der Stapel wächst „down“, und da die x86-Prozessoren little endian-Kodierung verwenden, ist die Wirkung von Anweisungen 4 bis 6, dass% esp (der Stapelzeiger) nun Punkte in einer Folge von zwölf Bytes, von Werten 2f 2f 62 69 6e 2f 73 68 00 00 00 00 (hexadezimal). Das ist die Codierung des „// bin / sh“ string (mit einem Abschluss Null und drei zusätzliche Nullen danach).
  8. Verschieben% esp% ebx. Jetzt% ebx enthält einen Zeiger auf den „// bin / sh“ Zeichenfolge, die oben gebaut wurde.
  9. Push% eax auf dem Stapel (% eax 0 zu diesem Zeitpunkt, es ist der zurückgegebene Status von setuid).
  10. Push% ebx auf dem Stapel (Zeiger auf "// bin / sh"). Anweisungen 8 und 9 zu bauen auf dem Stapel ein Array von zwei Zeigern, wobei die erste der Zeiger auf „// bin / sh“ und der zweite ein NULL-Zeiger. Das Array ist, was der execve Systemaufruf als zweites Argument verwenden.
  11. Verschieben% esp% ECX. Jetzt% ECX Punkte auf das Array gebaut mit Anweisungen 8 und 9.
  12. Sign-verlängern% eax in% edx:% eax. cltd ist die AT & T-Syntax für das, was die Intel Dokumentationen cdq nennen. Da% eax Null ist an diesem Punkt, diese Sätze% edx auf Null zu.
  13. Set% al (das am wenigsten signifikante Byte% eax) bis 11. Da% eax gleich Null war, der gesamte Wert von% eax ist jetzt 11.
  14. Systemaufruf. Der Wert der% eax (11) identifiziert, der den Systemaufruf als execve. execve erwartet drei Argumente, in% ebx (Zeiger auf eine Zeichenkette, die die Dateibenennung auszuführen),% ecx (Zeiger auf ein Feld von Zeigern auf Zeichenfolgen, die die Programmargumente sind, die erste, um eine Kopie des Programmnamens ist, um durch das aufgerufene Programm sich selbst) und% EDX (Zeiger auf ein Feld von Zeigern auf Zeichenketten verwendet werden, die die Umgebungsvariablen sind;. Linux diesen Wert NULL toleriert zu sein, für eine leere environment) bzw.

So ist der Code zuerst setuid(0) ruft, dann ruft execve("//bin/sh", x, 0) wo x auf ein Array von zwei Zeigern, erste einen Zeiger auf „// bin / sh“ zu sein, während die andere NULL ist.

Dieser Code ist ziemlich verworren, weil es will Nullen vermeiden: Wenn in binäre Opcodes zusammengebaut, die Folge von Befehls verwendet nur Nicht-Null-Bytes. Zum Beispiel, wenn die 12. Anweisung movl $0xb,%eax gewesen war (Einstellung der gesamten% eax bis 11), dann wird die binäre Darstellung dieses Opcode würde 0. Der Mangel an Null sorgt, dass Sequenz verwendbar als den Inhalt eines drei Bytes Wert enthalten haben C Zeichenfolge nullterminierte. Dies soll für fehlerhafte Programme durch Pufferüberlauf Angriff, natürlich.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top