
SMB1-Server zur NTLMv2-Hash-Interception, geschrieben in C.
SMB1-Server zum Abfangen von NTLMv2-Hashes, geschrieben in C.
Das Ziel des Projekts ist es, einen SMB1-Server als Zustandsmaschine zu implementieren, der Client-Anfragen korrekt annimmt und beantwortet, um ihn zu täuschen, sodass er eine NTLM-Authentifizierung abschließt und dadurch seinen eigenen NTLMv2-Hash preisgibt (in einem mit hashcat/john kompatiblen Format).
Tool für offensive Sicherheits-/Red-Team-Aktivitäten und für Bildungszwecke (Studium des SMB1/NTLM-Protokolls), ausschließlich für autorisierte Umgebungen, die dir gehören oder für die du eine ausdrückliche Genehmigung hast.
Der Server gibt sich als legitimer SMB1-Server aus und führt den Client durch eine 3-Phasen-Zustandsmaschine:

| Zustand | Übergang |
|---|---|
1. NEGOTIATE | Wenn ein SMB NEGOTIATE eintrifft, wechselt der Zustand nach der Antwort des Servers zu 2. CHALLENGE |
2. CHALLENGE | Wenn ein NTLM_NEGOTIATE eintrifft, wechselt der Zustand nach der Antwort des Servers zu 3. AUTH |
3. AUTH | Wenn ein NTLM_AUTH eintrifft, kehrt der Zustand nach der Antwort des Servers zu 1. NEGOTIATE zurück |
Auf Implementierungsebene muss der äußere NetBIOS-„Umschlag“ berücksichtigt werden, der aus 4 Bytes besteht, wobei die letzten 3 die Länge des SMB-Pakets in Bytes angeben.
Jede Client-Verbindung wird über eine Zustandsstruktur (client_t in server.h) verfolgt, die neben dem Status der Zustandsmaschine Folgendes verwaltet:
rx_buf) mit seiner Länge, um Daten zu puffern, die vom Socket gelesen, aber noch nicht vollständig verarbeitet wurden;tx_buf, mit Offset tx_off), um Daten zu puffern, die an den Client gesendet, aber noch nicht vollständig übertragen wurden;netbios_header_recv und netbios_msg_len zur Verfolgung des NetBIOS-Headers.Beim Empfang von Daten wird geprüft, dass mindestens 4 Bytes (NetBIOS-Header) empfangen wurden, die Länge der SMB-Nachricht bestimmt, die Zustandsfelder aktualisiert und schließlich die Nachricht verarbeitet, wobei der Zustand des Clients für den nächsten Empfang aktualisiert wird.
Die Hauptschleife des Servers basiert auf poll(), um mehrere Verbindungen gleichzeitig nicht-blockierend zu verwalten:

Wenn die NTLM-Authentifizierung abgeschlossen ist, gibt der Server auf dem Bildschirm ([INTERCEPTED] ...) den Benutzernamen, den Hostnamen, die Domäne und den erfassten NTLMv2-Hash im folgenden Format aus:
username::domain:server_challenge:ntlmv2_response:blob
bereit zur Verwendung mit Cracking-Tools wie hashcat (Modus -m 5600) oder john.
gcc/clang) und eine POSIX-Toolchain (der Code verwendet BSD-Sockets, poll(), signal() usw., ist also für Linux/Unix-ähnliche Umgebungen gedacht).Ein Makefile ist enthalten:
make # Hauptserver bauen -> ./impostor
make debug # Debug-Build (Symbole, -O0, AddressSanitizer/UBSan)
make clean # generierte Objektdateien und ausführbare Dateien entfernen
make run # Server bauen und ausführen
Alternativ lautet ein äquivalenter manueller Kompilierungsbefehl:
gcc -o impostor server.c smb1_parser.c spnego_decoder.c asn1_parser.c ntlm_parser.c
./impostor [port]
port (optional): TCP-Port, auf dem der Server lauscht. Wenn er weggelassen wird, wird der in server.h definierte Standardport (SERVER_PORT, 9000) verwendet. Er muss ein Wert zwischen 1 und 65535 sein.Beim Start gibt der Server ein Banner, die Version und Konfigurationsinformationen (Port, maximale Anzahl von Clients) aus und lauscht dann auf Verbindungen. Wenn ein NTLMv2-Hash erfasst wird, werden die abgefangenen Daten (Benutzername, Hostname, Domäne, Hash) auf dem Bildschirm ausgegeben. Der Server kann mit Ctrl+C (SIGINT) gestoppt werden, das von intHandler behandelt wird.
___ ___ _ ___
|_ _|_ __ ___ _ __ / _ \ ___| |_ / _ \ _ __
| || '_ ` _ \| '_ \| | | / __| __| | | | '__|
| || | | | | | |_) | |_| \__ \ |_| |_| | |
|___|_| |_| |_| .__/ \___/|___/\__|\___/|_|
|_| (v.1.0) by Lcky
[*] Version: 1.0
[*] Author: Lcky <luca9vinci at gmail dot com>
[*] Server Info
Port: 9090
Max Clients: 50
[*] Listening on port 9090
[*] Waiting for connections...
[INTERCEPTED] Username: test
[INTERCEPTED] Hostname: KALILINUX-2023-02
[INTERCEPTED] Domain : WORKGROUP
[INTERCEPTED] Hash : test::WORKGROUP:c4ba87a265de9e09:3482d0efa64fc09a94e44faa83d2a936:01010000000000009A3DE84B6235DD01D36FD06DFF4D64BB000000000200080038004E004900490001001E00570049004E002D00310046005800340055004D005000530034005400420004003400570049004E002D00310046005800340055004D00500053003400540042002E0038004E00490049002E004C004F00430041004C000300140038004E00490049002E004C004F00430041004C000500140038004E00490049002E004C004F00430041004C0008003000300000000000000000000000000000000CAFEB574B56CB6139E261228FBFE3075B4FA9393A3B71031AF3280F4D5A27D00A0010000000000000000000000000000000000009001C0063006900660073002F003100320037002E0030002E0030002E00310000000000
^C
[*] Stopping the server...
| Datei | Beschreibung |
|---|
server.c / server.h | Einstiegspunkt, TCP-Listener-Einrichtung, Client-Zustandsmaschine, Hauptschleife basierend auf poll(), RX/TX-Pufferung, Ausgabe abgefangener Hashes |
smb1_parser.c / smb1_parser.h | Parsen/Aufbauen von SMB1-Paketen (Header, NEGOTIATE, SESSION_SETUP-Befehle, Flags/Flags2 usw.) |
spnego_decoder.c / spnego_decoder.h | Dekodierung des SPNEGO-Tokens (Aushandlung des Authentifizierungsmechanismus, Extraktion des NTLMSSP-Blobs), das in SMB-Nachrichten enthalten ist |
asn1_parser.c / asn1_parser.h | Minimaler ASN.1-DER-Parser, der vom SPNEGO-Decoder verwendet wird, um die ASN.1-Strukturbaum aufzubauen |
ntlm_parser.c / ntlm_parser.h | Parsen von NTLMSSP-Nachrichten (NEGOTIATE, CHALLENGE, AUTHENTICATE) und Extraktion von Benutzername, Domäne, Hostname und NTLMv2-Antwort |
endianness.h | Dienstprogramm zur Behandlung der Byte-Reihenfolge (Little/Big-Endian-Konvertierungen zur Laufzeit) |
test.c, test2.c | Test-/Experimentierdateien für die Parser |
docs/ | Diagramme und unterstützendes Material (Zustandsmaschinen-Schema, Hauptschleife) |