Ruben Groenewoud

Linux-Erkennungsentwicklung mit Auditd

In diesem Artikel erfahren Sie mehr über die Verwendung von Auditd und Auditd Manager für die Erkennungstechnik.

28 Minuten LesezeitDetection Engineering, Enablement
Linux-Erkennungsentwicklung mit Auditd

Einführung

Unix- und Linux-Systeme arbeiten im Hintergrund und bilden unauffällig die Grundlage für einen bedeutenden Teil unserer technologischen Infrastruktur. Angesichts der zunehmenden Komplexität der Bedrohungen, denen diese Systeme ausgesetzt sind, ist die Gewährleistung ihrer Sicherheit wichtiger denn je.

Auditd gehört zu den grundlegenden Werkzeugen im Arsenal von Sicherheitsexperten, die in Unix- und Linux-Systemen arbeiten. Dieses leistungsstarke Tool dient der Überwachung und Aufzeichnung von Systemereignissen und bietet einen detaillierten Prüfpfad darüber, wer was wann getan hat. Es fungiert als Wächter, der patrouilliert und detaillierte Informationen über Systemaufrufe, Dateizugriffe und Systemänderungen aufzeichnet, die für forensische Analysen und die Echtzeitüberwachung von entscheidender Bedeutung sind.

Ziel dieses Artikels ist vielschichtig:

  1. Wir möchten Ihnen zusätzliche Informationen zu Auditd geben und seine Fähigkeiten sowie sein immenses Potenzial im Bereich der Sicherheitserkennungstechnik aufzeigen.
  2. Wir unterstützen Sie bei der Einrichtung von Auditd auf Ihren eigenen Systemen und passen es an Ihre spezifischen Überwachungsanforderungen an. Indem Sie verstehen, wie man Auditd-Regeln erstellt und ändert, lernen Sie, wie Sie genau das Verhalten erfassen, das Sie überwachen möchten, und die resultierenden Protokolle interpretieren, um Ihre eigenen Erkennungsregeln zu erstellen.
  3. Wir stellen Ihnen Auditd Manager vor, ein Integrationstool, das den Nutzen von Auditd erhöht, indem es die Verwaltung von Auditd über verschiedene Systeme hinweg vereinfacht.

Am Ende dieses Beitrags werden Sie nicht nur wissen, wie Sie Auditd Manager einsetzen, um einige unserer vordefinierten Erkennungsregeln in Ihre Sicherheitsstrategie zu integrieren, sondern auch ein umfassendes Verständnis von Auditd erlangen und lernen, wie Sie es nutzen können, um Ihre eigenen Erkennungsregeln zu erstellen.

Einführung in Auditd

Auditd ist ein Linux-Tool, das zur Überwachung und Aufzeichnung von Systemereignissen entwickelt wurde, um einen umfassenden Prüfpfad der Benutzeraktivitäten, Systemänderungen und Sicherheitszugriffe bereitzustellen. Auditd arbeitet, indem es sich in den Linux-Kernel einklinkt und detaillierte Informationen über Systemaufrufe und andere Systemereignisse erfasst, sobald diese auftreten. Diese Ereignisse werden dann in einer Datei protokolliert, wodurch ein mit einem Zeitstempel versehener Datensatz entsteht. Administratoren können Regeln definieren, die festlegen, welche Ereignisse protokolliert werden sollen, und haben so die Flexibilität, sich auf bestimmte Interessens- oder Problembereiche zu konzentrieren. Die protokollierten Daten können für eine Vielzahl von Zwecken verwendet werden, von Compliance-Audits bis hin zu detaillierten forensischen Analysen.

Auditd-Einrichtung

Für den Einstieg in Auditd bietet Elastic mehrere Optionen:

In diesem Artikel konzentrieren wir uns auf die beiden letztgenannten Optionen und nutzen den Elastic Agent, um Protokolle einfach in Elasticsearch zu importieren. Wenn Sie Elasticsearch noch nicht kennen, können Sie ganz einfach ein Elastic Cloud-Konto mit einer 30-tägigen Testlizenz erstellen. Alternativ können Sie für lokale Tests das Elastic Container Project herunterladen und den Lizenzwert in der .env-Datei auf „trial“ setzen. Datei.

Sie können die Schritte gerne mit Auditbeat oder Filebeat nachvollziehen – Anweisungen zur Einrichtung finden Sie in der oben verlinkten Dokumentation. Da die Auditd-Logs-Integration durch das Parsen der audit.log-Datei funktioniert, müssen Sie Auditd auf dem Linux-Host installieren, von dem Sie die Protokolle erfassen möchten. Je nach Linux-Distribution und gewähltem Paketmanager muss das Auditd-Paket installiert und der Auditd-Dienst gestartet und aktiviert werden. Für Debian-basierte Distributionen:

sudo apt update
sudo apt install auditd
sudo systemctl start auditd
sudo systemctl enable auditd

Die Datei /var/log/audit/audit.log sollte nun mit Auditd-Protokollen gefüllt sein. Als Nächstes müssen Sie die Auditd Logs-Integration installieren, in Fleet eine Agentenrichtlinie mit der neu installierten Integration erstellen und die Integration auf einen kompatiblen Elastic Agent mit installiertem Auditd anwenden.

Die Standardeinstellungen sollten für die meisten Anwendungsfälle ausreichen. Als Nächstes müssen Sie die Integration zu einer Agentenrichtlinie hinzufügen und die Agentenrichtlinie den Elastic Agents hinzufügen, von denen Sie Daten erfassen möchten. Der Elastic Agent sendet die Protokolle an logs-auditd.log-[Namespace]. Datenstrom. Sie können jetzt eine neue Datenansicht erstellen , die nur unsere eingehenden Auditd-Protokolle abgleicht.

Sie können nun die erfassten Auditd-Protokolle untersuchen. Wie Sie aber schnell feststellen werden, protokolliert Auditd standardmäßig nicht viel – Sie müssen Auditd-Regeln nutzen, um sein volles Potenzial auszuschöpfen.

Auditd rules

Auditd-Regeln sind Anweisungen, mit denen festgelegt wird, welche Systemaktivitäten überwacht und protokolliert werden sollen. Dies ermöglicht eine detaillierte Kontrolle über den Sicherheitsprüfungsprozess. Diese Regeln werden typischerweise in der Datei /etc/audit/audit.rules konfiguriert. Auditd-Regeln gibt es in 3 Varianten: control, file, und syscall. Weitere Informationen finden Sie hier.

Regeln vom Typ „Steuerung“

Der Steuerungstyp wird in den meisten Fällen verwendet, um Auditd zu konfigurieren, anstatt die zu überwachenden Ereignisse anzugeben. Standardmäßig enthält die Datei mit den Überwachungsregeln die folgenden Einstellungen für die Kontrolltypen:

-D
-b 8192
-f 1
--backlog_wait_time 60000
  • -D: Alle Regeln beim Start löschen (Auditd analysiert die Regeln in der Datei von oben nach unten). Durch das Entfernen aller Regeln beim Start wird eine saubere Konfiguration gewährleistet.
  • -b 8192: Die maximale Anzahl vorhandener Audit-Puffer im Kernel festlegen.
  • -f 1: Den Fehlermodus von Auditd auf Protokollierung setzen.
  • --backlog_wait_time 60000: Geben Sie die Zeitspanne (in ms) an, die das Auditsystem wartet, wenn das Limit für den Audit-Rückstand erreicht ist, bevor Audit-Datensätze gelöscht werden.

Dateisystemregeln

Aufbauend auf diesen Standardeinstellungen für den Steuerungstyp können Sie Dateisystemregeln erstellen, die manchmal auch als Überwachungsregeln bezeichnet werden. Mithilfe dieser Regeln können wir Dateien, die uns interessieren, auf Lese-, Schreib-, Änderungs- und Ausführungsaktionen überwachen. Eine typische Dateisystemregel sähe folgendermaßen aus:

-w [path-to-file] -p [permissions] -k [keyname]
  • -w: der Pfad zu der zu überwachenden Datei oder dem Verzeichnis.
  • -p: eine der Berechtigungen read (r), write (w), execute (e) oder change (a).
  • -k: der Name eines Schlüsselbezeichners, der verwendet werden kann, um die auditd-Protokolle leichter zu durchsuchen.

Falls Sie die Datei /etc/shadow auf Lese-, Schreib- und Änderungsvorgänge überwachen und diese Ereignisse unter einem Schlüssel namens shadow_access speichern möchten, können Sie die folgende Regel einrichten:

-w /etc/shadow -p rwa -k shadow_access

Systemaufrufregeln

Die wahre Stärke von Auditd zeigt sich erst bei der Arbeit mit seinen Systemaufrufregeln. Auditd-Systemaufrufregeln sind Konfigurationen, die festlegen, welche Systemaufrufe (syscalls) überwacht und protokolliert werden sollen. Dies ermöglicht eine detaillierte Nachverfolgung der Systemaktivität und der Interaktionen mit dem Betriebssystemkernel. Da jeder Systemaufruf abgefangen und mit der Regel abgeglichen wird, ist es wichtig, diese Funktionalität mit Bedacht zu nutzen, indem nur die relevanten Systemaufrufe erfasst werden und, wenn möglich, mehrere dieser Systemaufrufe in einer Regel zusammengefasst werden. Eine typische Systemaufrufregel würde folgendermaßen aussehen:

-a [action],[filter] -S [syscall] -F [field=value] -k [keyname]

Sie können das Flag -a gefolgt von action,filter verwenden, um auszuwählen, wann ein Ereignis protokolliert wird, wobei action entweder always (immer ein Ereignis erstellen) oder never (niemals ein Ereignis erstellen) sein kann.

Der Filter kann einer der folgenden Werte sein:

  • task: Protokolliert Ereignisse zur Aufgabenerstellung.
  • entry: Protokolliert Systemaufrufeinstiegspunkte.
  • exit: Protokolliert Systemaufruf-Exits/Ergebnisse.
  • user: Protokolliert Ereignisse im Benutzermodus.
  • exclude: Schließt Ereignisse von der Protokollierung aus.

Als Nächstes haben Sie:

  • -S: der Systemaufruf, an dem Sie interessiert sind (Name oder Systemaufrufnummer).
  • -F: ein oder mehrere Filter zur Auswahl der Übereinstimmungen.
  • -k: der Schlüsselbezeichner.

Mit den oben genannten Informationen sollten Sie die Grundlagen der meisten Auditd-Regeln verstehen können. Weitere Informationen und Beispiele für Werte, die diesen Regeln hinzugefügt werden können, finden Sie hier.

Der Einstieg in die Erstellung und das Testen einer umfassenden und dedizierten Auditd-Regeldatei für Ihre Organisation mag zunächst abschreckend wirken. Zum Glück gibt es auf GitHub einige gute Beispiele für öffentliche Regeldateien. Eine meiner Lieblingsvorlagen, auf der ich aufbauen kann, ist die von Neo23x0, die ein gutes Gleichgewicht zwischen Sichtbarkeit und Leistung bietet.

Ein Nachteil der Auditd Logs-Integration besteht darin, dass Auditd manuell auf jedem Host installiert werden muss, den Sie überwachen möchten, und die Regeldatei manuell auf jede laufende Auditd-Instanz angewendet werden muss. Das bedeutet, dass Sie die Regeldatei jedes Mal auf allen Hosts aktualisieren müssen, wenn Sie sie aktualisieren möchten. Heutzutage nutzen viele Organisationen Managementinstrumente, die diesen Prozess weniger zeitaufwändig gestalten können. Elastic bietet jedoch auch eine weitere Möglichkeit zum Einlesen von Auditd-Protokollen über die Auditd Manager-Integration, was den Verwaltungsaufwand verringert.

Einführung in Auditd Manager und dessen Einrichtung

Die Auditd Manager-Integration empfängt Audit-Ereignisse vom Linux Audit Framework , das Teil des Linux-Kernels ist. Durch diese Integration wird ein Abonnement für den Kernel eingerichtet, um die Ereignisse zu empfangen, sobald sie auftreten. Das Linux-Audit-Framework kann mehrere Meldungen für ein einzelnes prüfbares Ereignis senden. Beispielsweise veranlasst ein rename() -Systemaufruf den Kernel, acht separate Nachrichten zu senden. Jede Meldung beschreibt einen anderen Aspekt der laufenden Aktivität (den Systemaufruf selbst, Dateipfade, aktuelles Arbeitsverzeichnis, Prozesstitel). Durch diese Integration werden alle Daten aus den einzelnen Nachrichten zu einem einzigen Ereignis zusammengeführt. Weitere Informationen zu Auditd Manager finden Sie hier.

Darüber hinaus vereinfacht Auditd Manager die Verwaltung, da es eine zentrale Verwaltung über Fleet ermöglicht. Ein Update der Integration wird automatisch auf alle Elastic-Agenten angewendet, die Teil der geänderten Agentenrichtlinie sind.

Die Einrichtung der Auditd Manager-Integration ist einfach. Sie müssen sicherstellen, dass Auditd nicht mehr auf unseren Hosts ausgeführt wird, indem Sie den Dienst stoppen und deaktivieren.

sudo systemctl stop auditd
sudo systemctl disable auditd

Sie können nun die Auditd Logs-Integration aus unserer Agentenrichtlinie entfernen und stattdessen die Auditd Manager-Integration installieren/hinzufügen.

Für die Konfiguration der Integration stehen mehrere Optionen zur Verfügung. Der Auditd Manager bietet die Möglichkeit, die Audit-Konfiguration als unveränderlich festzulegen (ähnlich der Festlegung der Kontrolltypregel -e 2 in der Auditd-Konfiguration). Dies bietet zusätzliche Sicherheit, da nicht autorisierte Benutzer das Audit-System nicht ändern können, wodurch es schwieriger wird, böswillige Aktivitäten zu verbergen.

Sie können die Funktion „IDs auflösen“ nutzen, um die Auflösung von UIDs und GIDs in ihre zugehörigen Namen zu ermöglichen.

Für unsere Auditd-Regelverwaltung können Sie entweder die Regeln im Abschnitt „Audit-Regeln“ angeben oder eine Regeldatei verwenden und den Dateipfad angeben, aus dem diese Datei gelesen werden soll. Das Regelformat ähnelt dem Regelformat für die Auditd-Logs-Integration. Anstatt jedoch Kontrollflags in unserer Regeldatei anzugeben, können Sie diese Optionen stattdessen in den Integrationseinstellungen festlegen.

Auditd Manager löscht automatisch alle vorhandenen Regeln, bevor neue, in der Konfiguration angegebene Regeln hinzugefügt werden. Daher ist es nicht erforderlich, das Flag -D in der Regeldatei anzugeben. Zusätzlich können Sie unseren Fehlermodus in den Einstellungen auf silent setzen und müssen daher auch nicht das Flag -f angeben.

Sie können auch ein Limit für den Rückstand festlegen, was dem Setzen des -b -Flags entspricht.

Es gibt auch eine Option zum Einstellen der Gegendruckstrategie, die der Einstellung --backlog_wait_time entspricht.

Aktivieren Sie abschließend die Option zum Beibehalten des ursprünglichen Ereignisses, da dies die spätere Analyse des Ereignisses erleichtert.

Sie können die Integration nun speichern und sie auf die Agentenrichtlinie für die Hosts anwenden, von denen Sie Auditd-Protokolle erhalten möchten.

Fehlerbehebung bei Auditd-Regeldateien

Die von Neo23x0 bereitgestellte Regeldatei funktioniert standardmäßig nicht für Auditd Manager. Damit es funktioniert, müssen Sie einige kleinere Anpassungen vornehmen, wie z. B. das Entfernen der Kontrolltyp-Flags, eine UID-zu-Benutzer-Konvertierung für einen Benutzer, der auf Standardsystemen nicht vorhanden ist, oder einen redundanten Regeleintrag. Die notwendigen Änderungen werden letztendlich individuell auf Ihre Umgebung zugeschnitten sein.

Es gibt zwei Möglichkeiten, die Fehler zu identifizieren, die beim Kopieren und Einfügen einer inkompatiblen Datei in die Auditd Manager-Integration entstehen. Sie können zu dem Agenten navigieren, der die Police erhalten hat, und sich den Integrationseingabefehler ansehen. Sie können die Fehler einzeln analysieren und die fehlerhafte Zeile ändern oder entfernen.

Alternativ können Sie die Registerkarte „Discover“ verwenden, unsere Auditd Manager-Datenansicht auswählen und nach Ereignissen filtern, bei denen das Feld auditd.warnings vorhanden ist, und die Warnungen einzeln durchgehen.

Beispielsweise kann man sehen, dass die Fehlermeldung „unbekannter Regeltyp“ lautet, was darauf hindeutet, dass Auditd keine Kontrollregeln unterstützt. Der Fehler „Benutzer 'x' konnte nicht in eine numerische ID umgewandelt werden“ bedeutet, dass der Benutzer im System nicht existiert. Und schließlich bezieht sich „Regel 'x' ist ein Duplikat von 'x'“ auf doppelte Regeln. Nachdem Sie die widersprüchlichen Einträge entfernt haben und der Agentenstatus wieder „gesund“ ist, können Sie nun mit der Analyse von Auditd-Daten beginnen!

Analyse von Auditd Manager-Ereignissen

Nachdem die Auditd Manager-Daten nun in unserem Elasticsearch-Cluster verfügbar sind, können Sie, wie zuvor, eine Datenansicht für den Index logs-auditd_manager.auditd* erstellen, um diese Daten gezielt zu filtern. Unsere implementierte Regeldatei enthält folgenden Eintrag:

-w /etc/sudoers -p rw -k priv_esc

Hiermit werden Lese- und Schreibvorgänge für die Datei /etc/sudoers erfasst und diese Ereignisse in ein Protokoll mit dem Schlüssel priv_esc geschrieben. Lass uns den Befehl cat /etc/sudoers ausführen und das Ereignis analysieren. Betrachten wir zunächst einige der Felder, die allgemeine Informationen enthalten.

Man kann sehen, dass die Datei /etc/sudoers von der Binärdatei /usr/bin/cat über den Systemaufruf openat() aufgerufen wurde. Da der Dateibesitzer und die Gruppe root sind und der Benutzer, der den Zugriff auf diese Datei anfordert, nicht die UID 0 (root) ist, ist der Systemaufruf openat() fehlgeschlagen, was im Protokoll vermerkt ist. Schließlich können Sie das Tag sehen, das mit dieser spezifischen Aktivität verknüpft war.

Bei genauerer Betrachtung lassen sich weitere Informationen über das Ereignis finden.

Sie können die Befehlszeile des ausgeführten Prozesses sowie die Prozess-ID und die übergeordnete Prozess-ID sehen, die die Aktivität initiiert haben. Darüber hinaus können Sie sehen, von welcher Architektur das Ereignis ausging und über welches tty (Terminal, das mit der Standardeingabe verbunden ist) der Befehl ausgeführt wurde.

Um die a0-3-Werte zu verstehen, muss man sich eingehender mit Unix-Systemaufrufen befassen. Sie sollten an dieser Stelle wissen, was ein Syscall ist, aber um es vollständig zu erklären: Ein Unix-Syscall (Systemaufruf) ist eine grundlegende Schnittstelle, die es einem Programm ermöglicht, einen Dienst vom Kernel des Betriebssystems anzufordern, wie z. B. Dateioperationen, Prozesssteuerung oder Netzwerkkommunikation.

Schauen wir uns den openat() -Systemaufruf an. Beim Blick in die Manpage open(2) (Quelle) finden Sie folgende Informationen.

openat() ist eine weiterentwickelte Version des Systemaufrufs open() , die den Dateizugriff relativ zu einem Verzeichnisdateideskriptor (dirfd) ermöglicht. Dieser Systemaufruf ermöglicht es einem Programm, eine Datei oder ein Verzeichnis zu öffnen – eine entscheidende Operation für viele Systemaufgaben. Sie können sehen, dass der Systemaufruf Teil der Standard-C-Bibliothek ist und in der Headerdatei fcntl.h über die Include-Anweisung #include <fcntl.h> verfügbar ist.

Im Handbuch finden Sie folgende Syntax für den openat() -Systemaufruf:

int openat(int dirfd, const char *pathname, int flags, /* mode_t mode */);
  • dirfd gibt den Verzeichnisdateideskriptor an.
  • *pathname ist ein Zeiger auf den Namen der zu öffnenden Datei/des zu öffnenden Verzeichnisses.
  • flags Ermitteln Sie den Betriebsmodus (z. B. lesen, schreiben, erstellen usw.).

Um auf unser Ausgangsthema zurückzukommen: Sie sind nun in der Lage, die auditd.data.a0-a3 -Felder zu verstehen. Die Werte a0 bis a3 in einem auditd-Log repräsentieren die Argumente, die an einen Systemaufruf übergeben wurden. Diese Argumente sind entscheidend für das Verständnis des Kontextes und der Besonderheiten der Ausführung des Systemaufrufs. Lassen Sie uns nun genauer betrachten, wie diese Werte mit openat() zusammenhängen und was sie uns auf Grundlage unserer vorherigen Untersuchung über die versuchte Operation verraten.

  • auditd.data.a0 (dirfd): Der Wert a0, ffffff9c, kennzeichnet eine spezielle Direktive, AT_FDCWD, was darauf hindeutet, dass sich die Operation auf das aktuelle Arbeitsverzeichnis bezieht.
  • auditd.data.a1 (pathname): Der Wert a1 , 7ffd0f81871d, stellt eine hexadezimale Speicheradresse dar, die auf die Pfadnamenzeichenfolge der Zieldatei oder des Zielverzeichnisses verweist. In diesem Fall bezieht es sich auf den Versuch, auf die Datei /etc/sudoers zuzugreifen.
  • auditd.data.a2 (flags): Das Argument flags, das sich aus dem Wert a2 von 0 ergibt, gibt den Modus an, in dem auf die Datei zugegriffen werden soll. Da 0 anzeigt, dass keine speziellen Flags verwendet wurden, handelt es sich um eine Standardoperation – höchstwahrscheinlich einen reinen Lesezugriff.
  • auditd.data.a3 (mode): Der Wert a3 , ebenfalls 0, wird in Kontexten relevant, in denen die Datei erstellt wird, da er die Berechtigungen für die neue Datei festlegt.

Auf Grundlage der obigen Analyse haben Sie nun ein recht gutes Verständnis dafür, wie Auditd Manager-Ereignisse zu interpretieren sind.

Eine andere Möglichkeit, sich schnell einen Überblick über die Bedeutung eines Auditd Manager-Ereignisses zu verschaffen, besteht in der Verwendung des in Elastic integrierten KI-Assistenten. Führen wir den Befehl whoami aus und schauen wir uns das Feld auditd.messages innerhalb des Ereignisses an.

Sie können den Elastic AI Assistant bitten, die aufwendige Arbeit zu erledigen und das Ereignis zu analysieren. Anschließend müssen Sie nur noch im Handbuch für Systemaufrufe nachschlagen, um sicherzustellen, dass alles korrekt war. Erstellen wir zunächst eine neue Systemabfrage, die sich auf die Analyse von Auditd-Protokollen konzentriert und in etwa so aussieht:

Sie können nun die neu erstellte Systemeingabeaufforderung nutzen und Ihre Auditd-Nachricht ohne zusätzliche Formatierung dort einfügen. Sie erhalten dann die folgende Antwort:

Generative KI-Tools sind sehr nützlich, um eine schnelle Erklärung eines Ereignisses zu erhalten. Aber generative KI kann Fehler machen, deshalb sollten Sie sich stets bewusst sein, dass Sie bei der Verwendung von KI-Tools für diese Art von Analyse immer genau prüfen sollten, welche Ergebnisse sie erzeugt. Insbesondere dann, wenn die Ergebnisse dieser Tools zur Entwicklung von Erkennungsregeln genutzt werden, da bereits ein kleiner Fehler zu fehlerhafter Logik führen kann.

Beispiele für Erkennungsregeln des Auditd Managers

Nach dem Lesen des vorherigen Abschnitts sollten Sie nun über ausreichend Wissen verfügen, um mit der Analyse von Auditd Manager-Protokollen zu beginnen. Der aktuelle Regelsatz für die Elastic-Erkennung nutzt größtenteils die Elastic Defend-Integration, aber die Anzahl der Regeln, die Auditd nutzen, nimmt deutlich zu. In diesem Abschnitt werden verschiedene Erkennungsregeln, die Auditd nutzen, näher betrachtet, die Gründe dafür erläutert und einige wenig genutzte Techniken zum Schreiben von Abfragen für Erkennungsregeln vorgestellt.

Mögliche Reverse Shell über UDP

Die Regel „Potenzielle Reverse Shell via UDP“ zielt darauf ab, UDP-basierte Reverse Shells zu identifizieren. Da Elastic Defend derzeit keinen UDP-Datenverkehr erfasst, können Sie Auditd nutzen, um diese Transparenzlücke zu schließen. Die Regel basiert auf folgender Logik:

sample by host.id, process.pid, process.parent.pid
  [process where host.os.type == "linux" and event.type == "start" and event.action == "executed" and process.name : (
    "bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish", "perl", "python*", "nc", "ncat", "netcat", "php*",
    "ruby", "openssl", "awk", "telnet", "lua*", "socat"
    )]
  [process where host.os.type == "linux" and auditd.data.syscall == "socket" and process.name : (
    "bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish", "perl", "python*", "nc", "ncat", "netcat", "php*",
    "ruby", "openssl", "awk", "telnet", "lua*", "socat"
    ) and auditd.data.a1 == "2"]
  [network where host.os.type == "linux" and event.type == "start" and event.action == "connected-to" and
   process.name : (
    "bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish", "perl", "python*", "nc", "ncat", "netcat", "php*",
    "ruby", "openssl", "awk", "telnet", "lua*", "socat"
    ) and network.direction == "egress" and destination.ip != null and
   not cidrmatch(destination.ip, "127.0.0.0/8", "169.254.0.0/16", "224.0.0.0/4", "::1")]

Die Regel nutzt die Beispielfunktionalität , die eine chronologisch ungeordnete Abfolge von Ereignissen beschreibt und abgleicht. Dadurch wird sichergestellt, dass die Sequenz auch dann ausgelöst wird, wenn die Ereignisse in derselben Millisekunde auftreten. Zusätzlich nutzen wir einen Whitelisting-Ansatz, um verdächtige Binärdateien zu identifizieren, die in der Lage sind, eine umgekehrte Verbindung herzustellen, wodurch die Rate falsch positiver Ergebnisse minimiert wird.

Wir stellen die Erfassung von UDP-Verbindungen sicher, indem wir die Auditd-Daten im Zusammenhang mit dem socket() -Systemaufruf nutzen.

Wir sehen, dass der Wert a0 die Domäne darstellt, a1 den Typ und a2 das verwendete Protokoll. Unsere Regel nutzt die auditd.data.a1 == "2" -Syntax, die in den Typ SOCK_DGRAM übersetzt wird, der UDP ist.

Schließlich stellen wir sicher, dass wir nur ausgehende Netzwerkverbindungen vom Host erfassen und IPv4- und IPv6-Loopback-Adressen, IPv4-Link-Local- und Multicast-Adressen ausschließen. Außerdem sequenzieren wir die Abfrage mit process.pid und process.parent.pid , um sicherzustellen, dass die Ereignisse vom selben (übergeordneten) Prozess stammen.

Wenn wir nach verdächtigen Prozessen suchen wollen, die UDP-Sockets öffnen, können wir alle socket()-Systemaufrufe mit auditd.data.a1 == "2" abfragen, die Anzahl der verschiedenen Prozessvorkommen zählen und sie in aufsteigender Reihenfolge sortieren, um Anomalien zu finden. Dazu können wir diese ES|QL-Abfrage nutzen:

FROM logs-*, auditbeat-*
| EVAL protocol = CASE(
    auditd.data.a1 == "1", "TCP",
    auditd.data.a1 == "2", "UDP"
)
| WHERE host.os.type == "linux" and auditd.data.syscall == "socket" and protocol == "UDP"
| STATS process_count = COUNT(process.name), host_count = COUNT(host.name) by process.name, protocol
| SORT process_count asc
| LIMIT 100

Beim Blick auf die Ergebnisse lassen sich einige interessante Prozesse erkennen, die einen guten Ausgangspunkt für die Bedrohungsanalyse darstellen könnten.

Potential Meterpreter Reverse Shell

Eine weitere interessante Art von Reverse-Verbindungen, für die wir Auditd eingesetzt haben, ist die Erkennung der Meterpreter-Shell, einer beliebten Reverse-Shell, die innerhalb des Metasploit-Frameworks verwendet wird. Die Regel „Potenziell Meterpreter Reverse Shell“ nutzt das standardmäßige Host-Enumerationsverhalten von Meterpreter, um dessen Vorhandensein zu erkennen.

sample by host.id, process.pid, user.id
  [file where host.os.type == "linux" and auditd.data.syscall == "open" and auditd.data.a2 == "1b6" and file.path == "/etc/machine-id"]
  [file where host.os.type == "linux" and auditd.data.syscall == "open" and auditd.data.a2 == "1b6" and file.path == "/etc/passwd"]
  [file where host.os.type == "linux" and auditd.data.syscall == "open" and auditd.data.a2 == "1b6" and file.path == "/proc/net/route"]
  [file where host.os.type == "linux" and auditd.data.syscall == "open" and auditd.data.a2 == "1b6" and file.path == "/proc/net/ipv6_route"]
  [file where host.os.type == "linux" and auditd.data.syscall == "open" and auditd.data.a2 == "1b6" and file.path == "/proc/net/if_inet6"]

Beim Start sammelt Meterpreter standardmäßig Systeminformationen wie Rechner-, Benutzer- und IP-Routing-Informationen durch das Lesen bestimmter Systemdateien. Dieses Verhalten lässt sich beim Dekompilieren der Meterpreter-Payload beobachten, da die Pfade fest in die Binärdatei einprogrammiert sind.

Unsere Erkennungslogik nutzt auditd.data.a2 == “1b6”, da dies mit dem Verhalten des Meterpreters übereinstimmt. Wir können herausfinden, wie Meterpreter diese spezielle Systemaufrufkombination zum Lesen von Dateien nutzt, indem wir uns die Art und Weise ansehen, wie Meterpreter Dateihandler öffnet.

Nur zu Informationszwecken: Einige weitere Pfade, von denen Meterpreter liest, sind im folgenden Screenshot zu sehen.

Wir können ES|QL nutzen, um eine Reihe von Meterpreter-Reverse-Shells zu analysieren und leicht herauszufinden, auf welche Dateipfade von allen zugegriffen wird.

FROM logs-*, auditbeat-*
| WHERE host.os.type == "linux" and event.action == "opened-file" and process.name in ("shell-x64.elf", "JBNhk", "reverse.elf", "shell.elf", "elf") and auditd.data.a2 == "1b6"
| STATS file_access = COUNT_DISTINCT(process.name) by file.path
| SORT file_access desc
| LIMIT 100

In diesem Beispiel analysieren wir nur 5 Meterpreter-Shells, aber mit ES|QL können wir diese Analyse problemlos auf größere Zahlen ausweiten. Aus den obigen Informationen geht hervor, dass die für die Erkennungsregel ausgewählten Pfade in allen fünf Proben vorhanden sind.

Durch die Kombination der obigen Logik können wir möglicherweise Linux Meterpreter-Payloads entdecken.

Brute-Force-Angriff auf Linux FTP/RDP erkannt

Da es so viele verschiedene FTP/RDP-Clients für Linux gibt und die Authentifizierungsprotokolle nicht vollständig einheitlich implementiert sind, kann man das Feld auditd.data.terminal von Auditd nutzen, um verschiedene FTP/RDP-Implementierungen zu erkennen. Unsere FTP-Erkennungslogik sieht wie folgt aus:

sequence by host.id, auditd.data.addr, related.user with maxspan=3s
  [authentication where host.os.type == "linux" and event.action == "authenticated" and 
   auditd.data.terminal == "ftp" and event.outcome == "failure" and auditd.data.addr != null and 
   auditd.data.addr != "0.0.0.0" and auditd.data.addr != "::"] with runs=5

  [authentication where host.os.type == "linux" and event.action  == "authenticated" and 
   auditd.data.terminal == "ftp" and event.outcome == "success" and auditd.data.addr != null and 
   auditd.data.addr != "0.0.0.0" and auditd.data.addr != "::"] | tail 1

Hier sequenzieren wir 5 fehlgeschlagene Anmeldeversuche mit 1 erfolgreichen Anmeldeversuch auf demselben Host, von derselben IP-Adresse und für denselben Benutzer. Wir nutzen die tail- Funktion, die ähnlich wie tail in Unix funktioniert und die letzten X Warnmeldungen auswählt, anstatt alle Warnmeldungen innerhalb des Zeitraums auszuwählen. Dies hat keinen Einfluss auf die Benutzeroberfläche der SIEM-Erkennungsregeln; sie dient lediglich der besseren Lesbarkeit, da Brute-Force-Angriffe schnell zu einer Vielzahl von Warnmeldungen führen können.

Obwohl wir verschiedene FTP-Tools wie vsftpd verwenden, bleibt der Eintrag auditd.data.terminal über alle Tools hinweg ähnlich, sodass wir ein breiteres Spektrum an FTP-Brute-Force-Angriffen erfassen können. Unsere RDP-Erkennungsregel nutzt eine ähnliche Logik:

sequence by host.id, related.user with maxspan=5s
  [authentication where host.os.type == "linux" and event.action == "authenticated" and
   auditd.data.terminal : "*rdp*" and event.outcome == "failure"] with runs=10
  [authentication where host.os.type == "linux" and event.action  == "authenticated" and
   auditd.data.terminal : "*rdp*" and event.outcome == "success"] | tail 1

Da die auditd.data.terminal -Felder verschiedener RDP-Clients inkonsistent sind, können wir Wildcards verwenden, um ihre Authentifizierungsereignisse zu erfassen.

Netzwerkverbindung von Binärdatei mit RWX-Speicherbereich

Mit dem Systemaufruf mprotect() können die Zugriffsschutzmechanismen für einen bereits zugewiesenen Speicherbereich geändert werden. Dieser Systemaufruf ermöglicht es einem Prozess, die Berechtigungen von Seiten in seinem virtuellen Adressraum zu ändern, indem Berechtigungen wie Lesen, Schreiben und Ausführen für diese Seiten aktiviert oder deaktiviert werden. Ziel dieser Erkennungsregel ist es, Netzwerkverbindungen von Binärdateien zu erkennen, für die Lese-, Schreib- und Ausführungsberechtigungen für Speicherbereiche festgelegt sind. Schauen wir uns den Systemaufruf an.

Für unsere Erkennungsregellogik ist der Wert prot am wichtigsten. Man kann sehen, dass prot die folgenden Zugriffsflags haben kann:

Wie bereits erwähnt, ist prot eine bitweise ODER-Verknüpfung der Werte in der Liste. Für Lese-, Schreib- und Ausführungsberechtigungen benötigen wir also einen Integer-Wert von:

int prot = PROT_READ | PROT_WRITE | PROT_EXEC;

Dies entspricht nach der Bitumentransformation dem Wert 0x7 , und wir werden daher nach einer auditd.data.a2 == “7” suchen. Wir haben zwei Erkennungsregeln erstellt, die diese Logik nutzen - Unbekannte Ausführung von Binärdateien mit RWX-Speicherbereich und Netzwerkverbindung von Binärdateien mit RWX-Speicherbereich. Die Erkennungsregeln, die bestimmte Auditd-Konfigurationen nutzen, um zu funktionieren, enthalten in ihrer Einrichtungsanleitung einen Hinweis darauf, welche Regel hinzugefügt werden muss:

Die vorherige Methode nutzt den Regeltyp new_terms , der es uns ermöglicht, bisher unbekannte Begriffe innerhalb eines festgelegten Zeitfensters zu erkennen. Dies ermöglicht es uns, Binärdateien mit RWX-Berechtigungen zu erkennen, die zum ersten Mal auf einem bestimmten Host angezeigt werden, und gleichzeitig Fehlalarme für Binärdateien zu reduzieren, die zwar übermäßig permissive Berechtigungen haben, aber regelmäßig verwendet werden.

Letztere nutzt die folgende Erkennungslogik:

sample by host.id, process.pid, process.name
[process where host.os.type == "linux" and auditd.data.syscall == "mprotect" and auditd.data.a2 == "7"]
[network where host.os.type == "linux" and event.type == "start" and event.action == "connection_attempted" and
   not cidrmatch(destination.ip, "127.0.0.0/8", "169.254.0.0/16", "224.0.0.0/4", "::1")
]

Wir untersuchen einen Prozess, der mit diesen RWX-Berechtigungen ausgeführt wird, woraufhin eine Netzwerkverbindung (ausgenommen Loopback-, Multicast- und Link-Local-Adressen) hergestellt wird.

Interessanterweise weist Metasploit diese RWX-Berechtigungen häufig bestimmten Bereichen seiner generierten Payloads zu. Eines der Ereignisse, das diese Erkennungslogik in einem Test-Stack auslöst, hängt beispielsweise mit der Ausführung der Postgres-Payload von Metasploit für Linux zusammen. Bei der Analyse des Quellcodes dieser Payload kann man sehen, dass die Funktion payload_so die Flags PROT_READ, PROT_WRITE und PROT_EXEC definiert.

Anschließend werden einem bestimmten Speicherbereich mit einer bestimmten Seitengröße von 0x1000 die RWX-Zugriffsflags in ähnlicher Weise wie zuvor beschrieben zugewiesen.

Nach dem Ausführen der Payload und dem Abfragen des Stacks werden mehrere Treffer angezeigt, die alle mit Metasploit Meterpreter Payloads in Zusammenhang stehen.

Wenn wir uns auf die Postgres-Payload konzentrieren, die wir zuvor analysiert haben, können Sie den genauen Ausführungspfad der Payload mithilfe unseres visuellen Ereignisanalysators sehen. Elastic Security ermöglicht die Analyse jedes von Elastic Endpoint erkannten Ereignisses mithilfe eines prozessbasierten visuellen Analysators, der eine grafische Zeitleiste der Prozesse anzeigt, die zu der Warnung führten, sowie der Ereignisse, die unmittelbar danach auftraten. Die Untersuchung von Ereignissen im visuellen Ereignisanalysator ist hilfreich, um den Ursprung potenziell schädlicher Aktivitäten und anderer Bereiche in Ihrer Umgebung zu ermitteln, die möglicherweise kompromittiert sind. Es ermöglicht Sicherheitsanalysten außerdem, alle zugehörigen Hosts, Prozesse und andere Ereignisse detailliert zu untersuchen, um ihre Ermittlungen zu unterstützen.

Im Analyzer kann man sehen, wie Perl genutzt wird, um die jBNhk-Payload im Verzeichnis /tmp (mit RWX-Berechtigungen) zu erstellen und zu befüllen und eine Reverse-Meterpreter-Shell zu starten.

Fazit

In diesem Beitrag tauchen wir in die Welt von Auditd ein und erklären, was es ist und welchen Zweck es erfüllt. Wir haben Ihnen gezeigt, wie Sie Auditd einrichten und zum Laufen bringen, wie Sie diese Protokolle in Elasticsearch weiterleiten, um die Unix/Linux-Transparenz zu erhöhen und Ihre Fähigkeiten im Bereich der Linux-Erkennungstechnik zu verbessern. Wir haben darüber gesprochen, wie man Auditd-Regeln erstellt, um bestimmte Aktivitäten im Auge zu behalten, und wie man die dadurch generierten Ereignisse interpretieren kann. Um Ihnen die Arbeit zu erleichtern, haben wir Auditd Manager eingeführt, eine von Elastic entwickelte Integration, die Ihnen einen Teil der Verwaltungslast abnimmt. Zum Schluss haben wir verschiedene Erkennungsregeln und einige der Forschungsarbeiten, die zu ihrer Entwicklung beigetragen haben, näher betrachtet, damit Sie diese Datenquelle optimal nutzen können.

Wir hoffen, dass Ihnen dieser Leitfaden hilfreich war! Die Integration von Auditd in Ihre Unix-Systeme ist ein kluger Schritt für eine bessere Transparenz der Sicherheitslage. Egal, ob Sie sich für unsere vorkonfigurierten Erkennungsregeln entscheiden oder eigene erstellen, Auditd kann Ihre Unix-Sicherheit deutlich verbessern.