Skip to content
KitploitKITPLOIT
ToolsBlog
Einreichen
ToolsBlog
Einreichen

Hacking-, PenTest- und Cybersicherheits-Tools für Ihr Sicherheitsarsenal!

Kitploit ist ein Verzeichnis von Hacking-, Cybersicherheits- und Pentesting-Tools. Entdecken Sie die neuesten Projekt-Updates, um Schwachstellen zu finden, Systeme zu analysieren, Tests zu automatisieren und Ihre Sicherheit zu stärken.

··Feeds·Kontakt·Datenschutz·© 2026 Kitploit

Tool-Verzeichnis

Kategorien

Alle Kategorien anzeigen
Loading categories
cve-2010-4221-lab — Vom Patch zur RCE: handgefertigter Exploit für CVE-2010-4221 (ProFTPD TELNET IAC Stack-Overflow), mit der vollständigen, fehlergetriebenen Reise dokumentiert | Kitploit
Tools/GitHubGitHub/diegslva/cve-2010-4221-lab
Exploit-FrameworksSchwachstellenanalyseExploitationReverse EngineeringPenetrationstestsLernen & BildungBinary-ExploitationLabs & Praxis
GitHubdiegslva/cve-2010-4221-lab

cve-2010-4221-lab

Vom Patch zur RCE: handgefertigter Exploit für CVE-2010-4221 (ProFTPD TELNET IAC Stack-Overflow), mit der vollständigen, fehlergetriebenen Reise dokumentiert

Repository anzeigen
vor 12h 14mNoch nicht geprüft

Beliebteste

Alle anzeigen →

Entdecken Sie die meistgenutzten Tools unserer Community.

Alle Tools erkunden

Durchsuchen Sie unsere Tool-Sammlung

Alle Tools anzeigen →
Teilen

CVE-2010-4221 — ProFTPD TELNET IAC Stack Overflow: Vom Patch zur RCE

Ein vollständig reproduzierbares Labor und ein handgeschriebener Raw-Socket-Exploit für CVE-2010-4221 — den Stack-Pufferüberlauf vor der Authentifizierung in ProFTPDs pr_netio_telnet_gets() — aufgebaut als Lernübung in Schwachstellenforschung und Exploit-Entwicklung.

Jeder Fehlschlag ist dokumentiert. Der Happy Path ist eine Lüge; die Umwege sind die Lektion.


Rechtlicher und ethischer Hinweis — zuerst lesen

Dieses Repository ist ein pädagogisches Artefakt. Es existiert, damit Menschen, die sich keinen Mentor oder kein Training leisten können, lernen können, wie ein Memory-Corruption-Exploit tatsächlich entsteht: von einem Patch, über Fehlschläge, bis zu einem funktionierenden Proof of Concept innerhalb eines Labors, das dir gehört.

Red-Team-Arbeit — echte, professionelle offensive Sicherheit — ist durch ein einziges Wort definiert: Autorisierung. Alles, was ein Profi tut, geschieht innerhalb einer schriftlichen Vereinbarung: einem unterzeichneten Rules-of-Engagement-Dokument, das den Umfang, die Ziele, die erlaubten Techniken, das Zeitfenster und die Personen benennt, die es genehmigt haben. Ohne dieses Papier sind exakt dieselben Tastendrücke kein Beruf — sie sind in praktisch jeder Jurisdiktion der Erde ein Verbrechen.

Hier ist also der Vertrag für dieses Repo, nicht verhandelbar:

  • Führe dies nur gegen das beiliegende Docker-Labor oder Systeme aus, die dir gehören.
  • Niemals gegen etwas ohne ausdrückliche, schriftliche Autorisierung.
  • Wenn du lernst: willkommen, das wurde für dich gebaut.
  • Wenn du nach einer Waffe suchst, um sie gegen andere einzusetzen: schließe diesen Tab. Dieser Bug stammt aus 2010; er bringt dir nichts außer einem Strafregister.
  • Das Handwerk ist es wert, gelernt zu werden. Das Handwerk ist nur etwas wert mit der Disziplin, die damit einhergeht.


    Der Bug

    ProFTPD spricht TELNET-Escape-Sequenzen auf dem FTP-Kontrollkanal. In TELNET ist 0xFF (IAC, „Interpret As Command") das Escape-Byte; ein literales 0xFF wird als 0xFF 0xFF gesendet.

    pr_netio_telnet_gets() kopiert Client-Bytes in einen Stack-Puffer (pr_cmd_read's char buf[PR_DEFAULT_CMD_BUFSZ+1], 4104 Bytes mit glibcs MAXPATHLEN=4096), wobei der verbleibende Platz in buflen verfolgt wird — einer size_t, unsigned.

    Der verwundbare Pfad (1.3.3a, netio.c):

    root@kitploit:~
    case TELNET_IAC:
      switch (cp) {
        ...
        default:
          *bp++ = TELNET_IAC;   // write #1
          buflen--;             // decrement #1
          telnet_mode = 0;
          break;
      }
      break;
    ...
    *bp++ = cp;                 // write #2
    buflen--;                   // decrement #2  <-- no check in between
    

    Zwei Schreibvorgänge, zwei Dekremente, keine Nullprüfung dazwischen. Wenn buflen genau 1 ist, dekrementiert das Paar es auf 0, dann unterläuft es auf SIZE_MAX (18 Trillionen). Die Schleife glaubt nun, der Puffer sei unendlich und schreibt weiterhin angreiferkontrollierte Bytes den Stack hinauf — über gespeicherte Register, gespeichertes RBP und die Rücksprungadresse.

    Vor der Authentifizierung. Die Funktion läuft, bevor USER/PASS jemals verarbeitet werden.

    Der Patch

    Der Fix (Commit 3cc69b8388, „Bug#3521 - Telnet IAC processing stack overflow", veröffentlicht in 1.3.3c) umfasst zwölf Zeilen. Die gesamte Sicherheitsgrenze ist:

    root@kitploit:~
    if (buflen == 0) {
      break;
    }
    

    Siehe patch.diff. Den Patch zu lesen sagt dir, wo die Wunde war — das ist die Fähigkeit.

    Das Labor

    Das Dockerfile kompiliert ProFTPD 1.3.3a aus dem historischen Debian- Snapshot-Quellcode, absichtlich unsicher (so sah 2010 aus):

    • -fno-stack-protector — kein Canary
    • -z execstack — ausführbarer Stack (kein NX)
    • -no-pie — feste Binäradressen
    • Ausführung unter gdb, das ASLR standardmäßig deaktiviert → deterministischer Stack
    root@kitploit:~
    docker build -t proftpd-133a .
    docker rm -f lab133 2>/dev/null
    docker run -d --name lab133 --cap-add SYS_PTRACE \
      --security-opt seccomp=unconfined -p 127.0.0.1:2122:21 \
      proftpd-133a sh -c 'gdb -batch -ex "set follow-fork-mode child" \
      -ex "run" -ex "continue" --args /usr/local/sbin/proftpd -n -d1 \
      > /tmp/gdb.txt 2>&1; sleep 600'
    python3 exploit.py
    

    Erwartete Ausgabe:

    root@kitploit:~
    [S] 220 ProFTPD 1.3.3a Server (lab-iac) ...
    [S] THE SERVER SAID: b'PWNED!!PWNED!!'
    

    (Der Shellcode schreibt auf die FDs 0, 1 und 2, weil wir nicht davon abhängig sein wollten zu wissen, welcher den Kontrollkanal trägt — zwei von ihnen antworten.)

    Die Exploit-Architektur

    root@kitploit:~
    "SITE " + NOP-Sled + Shellcode + [\xff\xff-Flut] + Padding + [ret] + "\n"
     ^^^^^^^^^^^^^^^^^^^^                             ^^^^
     Shellcode lebt IM Befehls-               der Overflow-Schwanz liefert
     puffer — die Region, die                 nur EINE Adresse
     niemand anfasst
    
    1. „SITE " hält den FTP-Parser am Leben — der Befehl wird sauber verarbeitet.
    2. Der Shellcode ist der Inhalt des Befehls. Der Puffer ist der sicherste Ort auf dem Stack: nach dem Lesen wird nur buf[4102] berührt (Abschneidungs-NUL). Alles unterhalb der lebenden lokalen Variablen des Frames ist ruhig.
    3. Die IAC-Flut treibt buflen zum Unterlauf (siehe „Die Reise" für das Paritätsproblem).
    4. Der Ret-Slot (buf + 4152) erhält die Adresse der Mitte des NOP-Sleds. Wenn pr_cmd_read nach dem Parsen return 0 erreicht, landet die CPU im Sled und gleitet in den Shellcode.

    Diese invertierte Architektur — Payload zuerst, Flut zweitens, Adresse zuletzt — wurde gegen das kanonische Metasploit-Modul validiert (proftp_telnet_iac), das dasselbe Layout verwendet. Deren Ziele hatten NX, also brauchten sie eine ROP-Kette mit einem „vierfachen Deref" des res-Zeigers; unser Labor hat einen ausführbaren Stack, also genügt ein einzelner direkter Return.

    Die Reise (der eigentliche Sinn dieses Repos)

    Der finale Exploit umfasst 60 Zeilen. Was er kostete:

    1. Blinde \xff-Flut → nichts. Der Server beendete die Sitzung höflich. Grundursache: buflen startet bei 4102 (GERADE) und jedes IAC-Paar dekrementiert um 2 — es landet sauber auf 0, nie auf 1. Der Unterlauf benötigt eine gebrochene Parität. Lektion: das Lesen der Zustandsmaschine schlägt das Sprühen.

    2. Falsche Puffergröße. Erster kalibrierter Versuch nahm einen 1024-Byte-Puffer an. Der echte ist MAXPATHLEN+8 = 4104 auf Linux/glibc. Die Flut stoppte 3 KB vor dem Ziel. Lektion: miss das Ziel, nimm das Ziel nicht an.

    3. Erster SIGSEGV. Zyklisches De-Bruijn-Muster (Aa0Aa1...) platzierte den Ret-Slot bei buf+4152, zweifach kreuzvalidiert (Frame-Mathematik + Muster- Offset). Lektion: das zyklische Muster ist ein Maßband, kein Exploit.

    4. RIP-Kontrolle. Das Setzen des Slots auf 0x4141414141414141 ließ die ret-Instruktion selbst abstürzen — x86-64 verweigert nicht-kanonische Adressen, und der Fehler landet auf ret, wobei unser Wert im Backtrace wartet. Lektion: ein Absturz bei ret mit deinem Wert im Frame = Kontrolle.

    5. Shellcode oberhalb des Ret-Slots → überschrieben. 8 Bytes durch einen Heap-Zeiger überschrieben (0x4d7838 — später als die cmd_rec-Pool- Allokation identifiziert). Die Stack-Frames oberhalb des Slots gehören zu Funktionen, die zwischen Landung und Hijack noch arbeiten. Lektion: der Overflow ist nicht der letzte Schreibvorgang; das Programm lebt weiter auf dem Stack, den du gerade vandalisiert hast.

    6. „Tote Zone" unterhalb des Slots → ebenfalls beschrieben. pr_cmd_read's eigene lokale Variablen (cmd, buflen, cp) leben genau dort und werden während des Parsens weiterhin gespeichert.

    7. Hardware-Watchpoint-Forensik. watch *(long*)ADDR in gdb verwandelte das Rätsel in eine Kamera: jeder Schreibvorgang auf die überschriebene Adresse, mit Backtrace, in Reihenfolge. Lektion: wenn die Frage „wer hat diesen Speicher geschrieben?" ist, ist die Antwort einen gdb-Befehl entfernt.

    8. Lies die Referenz, dann verstehe sie. Das kanonische Modul bestätigte die invertierte Architektur. Einen anderen Exploit nach dem Aufbau deines eigenen mentalen Modells zu lesen ist Studium; davor ist es Kopieren.

    Gelernte Lektionen

    • size_t wird nie negativ — es wird gigantisch. Integer-Unterlauf in einem Zähler für verbleibenden Platz ist ein Stack-Overflow mit Extraschritten.
    • Parität ist eine Waffe. Wenn ein Primitive um 2er-Schritte dekrementiert, kontrollierst du den Unterlauf durch Kontrolle von ungerade/gerade, nicht nur der Größe.
    • Bad Chars sind eine Protokollfrage. Unser Shellcode vermeidet \x0a (beendet das Lesen) und überlebt \xff (TELNET-Escape) konstruktionsbedingt.
    • Prefork-Server verzeihen Abstürze. Das Kind stirbt, der Elternprozess akzeptiert weiter: unendliche Versuche. Zuverlässigkeitstechnik ist Teil des Exploits.
    • Messe und exploite dasselbe Artefakt. Ein Unterschied von 11 Bytes in argv[0] (Build-Tree-Binary vs. installierte Binary) verschob den gesamten Stack um 0x40 und machte einen perfekten Exploit stillschweigend ungültig.
    • Der Signal-Handler gesteht. ProFTPD fängt SIGSEGV und protokolliert „terminating (signal 11)" — das Ziel sagt dir, dass es gestorben ist, selbst wenn der Kernel still bleibt.

    Referenzen

    • Fix-Commit: https://github.com/proftpd/proftpd/commit/3cc69b8388
    • CVE: https://nvd.nist.gov/vuln/detail/CVE-2010-4221
    • Kanonisches Modul: modules/exploits/linux/ftp/proftp_telnet_iac.rb (rapid7/metasploit-framework)
    • Schwesterlabor (Logik-Bug, gleicher Daemon): CVE-2015-3306 mod_copy

    Autor

    Erstellt von diegslva, öffentlich lernend — von „nie einen Exploit geschrieben" zu Pre-Auth-RCE mit handgerolltem Shellcode, an einem dokumentierten Tag. Wenn dieses Repo dir etwas beigebracht hat, gib es weiter.

    Tool herunterladen