Aus Linux-Magazin 01/2019

Forensische Hauptspeichernalyse mit Volatility

© Alexandr Ozerov, 123RF

Wer nach einem Einbruch den Arbeitsspeicher eines Rechners untersuchen muss, darf sich der tatkräftigen Unterstützung des Python-Framework Volatility versichern. Es analysiert wichtige Speicherstrukturen und hilft dabei, die flüchtigen Spuren eines Angriffs zu lesen.

Wer an IT-Forensik denkt, hat meist die Analyse von nicht-flüchtigen Datenträgern, wie Festplatten oder SSDs vor Augen. Doch auch der flüchtige, also der volatile, Arbeitsspeicher ist einen Blick wert. Er enthält meist wichtige Spuren, etwa zu Prozessen oder Netzwerkverbindungen, und gibt so Hinweise auf einen erfolgreichen Angriff.

Vor der eigentlichen Detektivarbeit steht das Anfertigen eines RAM-Images. Diesen so genannten Memory Dump gilt es dann zu analysieren. Mit Linux-Bordmitteln können Anwender bereits einiges herausfinden und lernen – allerdings ist das auch recht zeitaufwändig. Unterstützung gibt es daher von Volatility [1]. Das in Python geschriebene Framework identifiziert die wichtigsten Speicherstrukturen eines Betriebssystems und bereitet die Inhalte in für Menschen lesbarer Form auf. Sein großes Plus sind die vielen Plugins, welche die verschiedensten Analyse-Tätigkeiten unterstützen (Tabelle 1).

Tabelle 1

Volatility-Erweiterungen

Plugin

Funktion

Prozesse

linux_apihooks

Checkt auf Userland-API-Hooks

linux_bash

Extrahiert aus dem Prozess-Speicher die Bash-History

linux_check_creds

Schaut, ob sich Prozesse Credential Structures teilen

linux_dump_map

Schreibt ausgewählte Memory Mappings auf eine Disk

linux_dynamic_env

Holt dynamische Umgebungsvariablen eines Prozesses wieder

linux_getcwd

Zeigt pro Prozess dessen aktuelles Verzeichnis

linux_kernel_opened_files

Vom Kernel geöffnete Files

linux_library_list

Bibliotheken, die ein Prozess geladen hat

linux_librarydump

Kopiert die Shared Libraries eines Prozesses auf Disk

linux_list_raw

Listet Prozesse mit verdächtigen Sockets

linux_malfind

Schaut nach verdächtigen Process Mappings

linux_memmap

Zeigt die Memory Map von Linux-Tasks

linux_plthook

Scannt PLT von ELF-Binaries auf unnötige Hooks

linux_proc_maps

Memory Maps eines Prozesses

linux_procdump

Schreibt das Executable eines Prozesses auf Disk

linux_process_hollow

Prüft auf Anzeichen für Process Hollowing

linux_psaux

Prozesse mit Startzeit und ganzer Kommanozeile

linux_psenv

Prozesse mit ihren statischen Umgebungsvariablen

linux_psscan

Scannt den RAM von Prozessen

Kernel und Scheduling

linux_check_idt

Schaut, ob sich die IDT geändert hat

linux_check_inline_kernel

Sucht nach Inline-Kernelhooks

linux_check_modules

Vergleicht die Module-Liste mit Sys-FS-Angaben

linux_check_syscall

Check, ob sich die Systemcall-Tabelle geändert hat

linux_check_tty

Sucht nach Hooks auf TTY-Devices

linux_hidden_modules

Durchforstet den RAM nach versteckten Kernelmodulen

linux_info_regs

Wie »info registers« in GDB

linux_lsmod

Geladene Kernelmodule

linux_moddump

Extrahiert geladene Kernelmodule

linux_pslist

Aktive Tasks aus der »task_struct->task«-Liste

linux_pslist_cache

Wie »linux_pslist«>, aber aus »kmem_cache«

linux_pstree

Zeigt Eltern-Kind-Beziehung zwischen Prozessen

linux_psxview

Sucht versteckte Prozesse

linux_threads

Zeigt die Threads eines Prozesses

imagecopy

Kopiert einen physischen Addressbereich in ein Image

Files und Dateisysteme

linux_check_fop

Findet von Rootkits modifizierte File Operation Structures

linux_dentry_cache

Sammelt Files aus dem Dentrycache

linux_enumerate_files

Liste mit File-Referenzen aus den Dateisystem-Cache

linux_elfs

Findet ELF-Binaries in Process Mappings

linux_find_file

Listet Dateien und stellt sie aus dem RAM wieder her

linux_lsof

Listet Filedeskriptoren

linux_mount

Gemountete Dateisysteme bzw. Devices

linux_mount_cache

Wie »linux_mount«, aber aus dem »kmem_cache«

linux_recover_filesystem

Stellt RAM-gecachtes Dateisystem wieder her

linux_tmpfs

Stellt Tmp-FS wieder her

linux_truecrypt_passphrase

Stellt gecachte Truecrypt-Passphrases wieder her

mbrparser

Scannt nach Master Boot Records

Netzwerk

linux_arp

Zeigt die ARP-Tabelle

linux_check_afinfo

Prüft Operation Function Pointers der Netzwerkprotokolle

linux_ifconfig

Aktive Interfaces

linux_netfilter

Listet Netfilter-Hooks

linux_netscan

Untersucht Netzwerk-Structures

linux_netstat

Listet offene Sockets

linux_route_cache

Stellt Routing-Cache wieder her

linux_sk_buff_cache

Stellt Pakete aus »sk_buff kmem_cache« wieder her

Abgebildet

Der erste Schritt besteht im Erzeugen eines Speicherabbildes. Läuft das eventuell kompromittierte System in einer virtuellen Maschine, kann der Virtual Machine Manager einen Snapshot erstellen, den geeignete Tools dann auseinandernehmen [2],[3]. Ein Bare-Metal-Linux stellt Forensiker vor größere Herausforderungen: Jede Änderung am System ändert auch den Speicherinhalt, was Spuren vernichten könnte.

Der Ansatz, den Speicher im Labor abzukühlen und in einem Spezialgerät auszulesen [4], ist nicht praktikabel. Hat der Rechner einen Firewire-Anschluss, ließe sich eine Sicherheitslücke ausnutzen und der Speicher über den Bus kopieren [5]. Das wird auch für Thunderbolt und PCIe diskutiert, klappt allerdings unter Linux noch nicht so recht [6],[7],[8].

Damit bleibt nur, doch eine Speicherveränderung in Kauf zu nehmen. Bei älteren Linux-Versionen ging das recht simpel, denn »dd« konnte »/dev/mem« lokal auf USB-Sticks oder per »netcat« übers Netzwerk kopieren. Neuere Distributionen schränken die Leserechte allerdings erheblich ein, was aus Sicherheitssicht eine gute Idee ist. Hier hilft beispielsweise der Linux Memory Grabber [9] weiter.

Abgegriffen

Das Skript »lmg« setzt voraus, dass ein Linux-Rechner verfügbar ist, der ein zum Zielsystem passendes Kernelmodul kompilieren kann, erfordert also detaillierte Kenntnisse über das Ziel und einen Rootaccount. In vielen Fällen müssen Forensiker hier passen, es sei denn, ein eigenes System ist betroffen. Dann hilft die Anleitung unter [9] dabei, zu einem Speicherabbild zu gelangen. Zwar verändert die Installation des Kernelmoduls den Speicherinhalt des Zielsystems, und »lmg« greift noch dazu auf Binarys des Zielsystems zurück, was bei einem geknackten System nicht ganz ohne ist, doch dürfte es in den meisten Fällen die einzige gangbare Lösung sein.

Wer bezüglich modifizierter Binarys besonders vorsichtig sein will, könnte sie auf dem USB-Stick mitbringen, vor der Installation eine weitere Speicheränderung in Kauf nehmen und den Pfad so ändern, dass die Programme vom Stick zum Einsatz kommen. Erste Hinweise, ob eine solche Maßnahme nötig ist, erhalten Admins von einem Host-based Intrusion Detection System [10]. Besonders sichere Lösungen wie etwa die in [11] vorgeschlagene gibt es für Linux derzeit nicht. Das ist bei forensischen Untersuchungen ärgerlich, dafür im Alltag durchaus ein Sicherheitsgewinn, denn auch Angreifer könnten solche Hintertüren ausnutzen.

Spurensicherung

Der Admin, der nun im Besitz eines Speicher-Images seines möglicherweise kompromittierten Rechners ist, darf sich jetzt der eigentlichen Analyse zuwenden. Wer Volatility aus den Quellen installieren möchte, benötigt zahlreiche Python-Module. Alternativ gibt es auf der Projektseite [1] fertige Binarys für gängige Betriebssysteme. Anwender entpacken lediglich die Zip-Datei, und das Tool ist einsatzbereit. Wer den langen Namen unhandlich findet, erstellt flugs einen Symlink:

ln -s volatility_2.6_lin64_standalone vol

Außerdem bietet es sich an, ein Unterverzeichnis namens »profiles« anzulegen. Hier ist Platz für Profile der zu analysierenden Systeme. Um ein Speicherabbild auswerten zu können, benötigt Volatility Informationen zum Layout des Speichers. Ein Profil muss also immer exakt zur Kernelversion passen. Das Wiki [12] verlinkt fertige Linux-Profile und zeigt, wie Benutzer mittels »dwarfdump« die nötigen Informationen über Kerneldatenstrukturen und Debugsymbole generieren, um eigene Profile zu erzeugen.

Gut eingerichtet

Für alle Tests in diesem Artikel kommt ein fertiges Speicherabbild von [13] zum Einsatz. Nach dem Download und Auspacken der Zip-Datei finden Anwender ein Unterverzeichnis namens »linux«. Das dort enthaltene Archiv »book.zip« sollte in den zuvor angelegten Ordner »profiles« wandern – ob per »mv«, »cp« oder als Hardlink ist Geschmacksache; lediglich ein Symlink funktionierte auf dem Testrechner nicht. Der Befehl

./vol --plugin=profiles/ --info | grep -i book

sollte die folgende Ausgabe liefern:

Volatility Foundation Volatility Framework 2.6
Linuxbookx64 - A Profile for Linux book x64

Findet Volatility das Profil nicht, ist womöglich das »plugin«-Verzeichnis falsch angegeben. Wer mehrere Ordner durchsuchen möchte, trennt diese mit einem Doppelpunkt voneinander ab.

Tippfaule Anwender legen außerdem eine Konfigurationsdatei für Volatility an, was ihnen die Eingabe langer Parameter erspart und es ermöglicht, die Einstellungen später zu rekonstruieren. Das Tool erwartet seine Einrichtung entweder in »~/.volatilityrc« oder im aktuellen Verzeichnis in der Datei »volatilityrc«. Listing 1 zeigt ein Beispiel, welches das Pluginverzeichnis, ein Profil sowie ein Abbild definiert. Alternativ geben Benutzer das Image beim Aufruf hinter »-f« an:

./vol --plugin=profiles/ --profile=Linuxbookx64 -f AMF_MemorySamples/linux/linux-sample-1.bin

Die Reihenfolge der Parameter ist wichtig: Steht »–profile« vor »–plugin«, findet das Tool das Profil nicht. Wer in der Konfigurationsdatei einen Pfad zu den Profilen angibt, sollte das Profil auch benennen, denn die Kommandozeilenoptionen haben Vorrang vor der Einrichtungsdatei.

Listing 1

volatilityrc

01 [DEFAULT]
02 PLUGIN=profiles/
03 LOCATION=file://AMF_MemorySamples/linux/linux-sample-1.bin
04 PROFILE=Linuxbookx64

Vertrauensfrage

Ein erster Blick ins Speicherabbild mit dem Befehl »./vol linux_pslist« liefert die Liste à la »ps«. Analog dazu kennt das Tool »linux_psaux«, »linux_psenv« und »linux_pstree« (Abbildung 1). Die Listen kommen aus einer (in »sched.h« definierten) Datenstruktur, in welcher der Kernel Prozesse verwaltet.

Kernelprozesse lassen sich leicht daran erkennen, dass sie keinen Adressübersetzungs-Eintrag in der Directory Table Base (DTB) haben. Doch ist diese Ausgabe vertrauenswürdig? Könnte ein Angreifer sie manipulieren? Ein einfacher Ansatz zum Tarnen findet sich in Sourcen älterer Kernelversionen in der Datei »base.c«:

res = access_process_vm(task, mm->arg_start, buffer, len, 0);

Für einen Eintrag in der Prozessliste liest der Kernel also die Umgebungsvariablen der Shell aus. Ein Prozess, der sein Environment manipuliert, könnte also unter anderem Namen auftauchen.

Da Forensiker immer davon ausgehen müssen, dass Angreifer die Ziele mindestens so gut kennen wie sie selbst, gilt es also, die ermittelte Prozessliste zu verifizieren. Dazu bietet Volatility das Kommando »linux_psscan«, das nicht die Kerneldatenstrukturen nach Prozessen durchsucht, sondern den ganzen Speicher, wo sich ein Angreifer schlechter verstecken kann. Der manuelle Abgleich von »linux_pslist« und »linux_psscan« ist aber nicht erforderlich, denn »linux_psxview« liefert eine übersichtliche Tabelle, wo Prozesse aufgetaucht sind.

Wer die Kommandos auf das Beispielimage loslässt, stellt fest, dass »linux_psscan« zahlreiche Prozesse anzeigt, die »linux_pslist« nicht findet. Das können Threads sein, die das Volatility-Plugin »linux_threads« identifizieren kann. Doch nicht immer gibt es sofort eine plausible Erklärung. Der Prozess »swapper« beispielsweise fehlt in beiden Listen, was als Teil des Schedulers – er verwaltet »idle« – sicher zulässig ist.

Abbildung 1: Die von Volatility mit dem Kommando »linux_pstree« erzeugte Ausgabe ist ähnlich der von »pstree«.

Abbildung 1: Die von Volatility mit dem Kommando »linux_pstree« erzeugte Ausgabe ist ähnlich der von »pstree«.

Rootkits aufspüren

Manchmal ist es hilfreich, sich zunächst einen Überblick zu verschaffen. Admins, die sich fragen, ob der Rechner mit einem Rootkit infiziert ist [14], können ebenfalls zu Volatility greifen. Die Toolsammlung hat gleich mehrere Plugins, die dazu Auskunft geben können. Der Befehl

./vol --plugin=profiles/ linux_check_idt

etwa liefert die Interrupt-Descriptor-Tabelle (Abbildung 2). Wenn hier ein Eintrag umgeleitet (Hooked) ist, spricht einiges für ein manipuliertes System. Gleiches gilt für die Exception-Handler und die Systemcalls. Genau wie »lsof« schaut »linux_lsof« nach offenen Dateien eines Prozesses. »linux_chk_tty« und »linux_keyboard_notifier« hingegen prüfen, ob ein Angreifer auf typische Weise einen Keymapper installiert hat. Volatility ermittelt zudem die ARP-Table, offene Netzwerkverbindungen, gemountete Dateisysteme oder eingesetzte Kernelmodule – es gibt für fast alles Plugins (Komplettübersicht im Wiki über Github).

Warum sollte ein Admin also zu Volatility greifen, wenn er auf der Suche nach Rootkits ist, und nicht zu einem speziellen Malware-Scanner, der die Festplatte analysiert? Ein Rootkit, dass im Speicher ist, kann die Prüfung nicht mehr stören. So erhöhen sich die Chancen, den Angreifer zu entdecken. Ist ein suspekter Prozess identifiziert, gibt »linux_proc_maps« den Speicherinhalt zur besseren Analyse aus.

Abbildung 2: Hier scheint alles in Ordnung: Die Interrupt-Service-Routinen sind nicht umgeleitet.

Abbildung 2: Hier scheint alles in Ordnung: Die Interrupt-Service-Routinen sind nicht umgeleitet.

Interpretationspflicht

Zum Nachweis von Nutzer-Fehlverhalten eignet sich die Analyse der Bash-History (Abbildung 3). Volatility entdeckt auch Kommandos, wenn zum Vertuschen der letzten Eingaben die Länge der History auf 0 und ihr Speicherort nach »/dev/null« verlegt wurde.

Die wahre Herausforderung beim Einsatz von Volatility ist wie bei allen Analysetools weniger der Einsatz der korrekten Parameter – viel schwieriger ist es, die Ausgaben des Programms richtig zu interpretieren. Hier hilft nur Übung und eine gute Kenntnis des Systems mit allen seinen Datenstrukturen. (jk/hej)

Abbildung 3: Deutlich sichtbar: Hier hat der Forensiker das Speicherabbild mit »lime« gezogen.

Abbildung 3: Deutlich sichtbar: Hier hat der Forensiker das Speicherabbild mit »lime« gezogen.

Infos

  1. Volatility: https://www.volatilityfoundation.org

  2. Volatility und VMware: https://github.com/volatilityfoundation/volatility/wiki/VMware-Snapshot-File

  3. Volatility und Virtualbox: https://github.com/volatilityfoundation/volatility/wiki/Virtual-Box-Core-Dump

  4. Sergei Skorobogatov, “Low temperature data remanence in static RAM”:https://www.cl.cam.ac.uk/techreports/UCAM-CL-TR-536.pdf

  5. Michael Becher, Maximillian Dornseif, Christian N. Klein, “FireWire, all your memory are belong to us”:https://cansecwest.com/core05/2005-firewire-cansecwest.pdf

  6. Ulf Frisk, “DMA attacking over USB-C and Thunderbolt 3”: http://blog.frizk.net/2016/10/dma-attacking-over-usb-c-and.html

  7. Inception: https://github.com/carmaa/inception

  8. Joe FitzPatrick, Miles Crabill, “Stupid PCIe Tricks featuring NSA Playset: PCIe”:https://www.youtube.com/watch?v=OD2Wxe4RLeU

  9. Linux Memory Grabber: https://github.com/halpomeranz/lmg

  10. Tobias Eggendorfer, “Haltet den Dieb!”: Linux-Magazin 10/15, S. 22

  11. Johannes Stuttgen, Michael Cohen, “Anti-Forensic Resilient Memory Acquisition”:http://dfrws.org/sites/default/files/session-files/paper-anti-forensic_resilient_memory_acquisition.pdf

  12. Volatility-Profile für Linux: https://github.com/volatilityfoundation/volatility/wiki/Linux

  13. The Art of Memory Forensics: https://www.memoryanalysis.net/amf

  14. Jürgen Quade, “Spitzel im Inneren”: Linux-Magazin 10/12, S. 34

Der Autor

Tobias Eggendorfer ist Professor für IT-Sicherheit und freiberuflicher IT-Berater (http://www.eggendorfer.info). Wenn er IT-Forensik lehrt, stöhnen seine Studenten ab und zu, weil längst vergessenes Wissen aus Grundlagenvorlesungen plötzlich wieder wichtig ist. Genau das macht aber die IT-Forensik und -Sicherheit so spannend.

DIESEN ARTIKEL ALS PDF KAUFEN
EXPRESS-KAUF ALS PDFUmfang: 4 HeftseitenPreis €0,99
(inkl. 19% MwSt.)
LINUX-MAGAZIN KAUFEN
EINZELNE AUSGABE Print-Ausgaben Digitale Ausgaben
ABONNEMENTS Print-Abos Digitales Abo
TABLET & SMARTPHONE APPS Readly Logo
E-Mail Benachrichtigung
Benachrichtige mich zu:
0 Kommentare
Älteste
Neuste Beste Bewertung
Nach oben