Inhalt
1. Einführung
Die vorläufige Veröffentlichung der OWASP Top 10 - 2017 im April 2017 hat für einige Kontroversen über die Aufnahme eines neuen Eintrags mit dem Titel “A7 - Insufficient Attack Protection” (Unzureichender Angriffsschutz) gesorgt.
Abgesehen von taxonomischen Problemen (ein fehlender Schutz ist an sich keine Schwachstelle) empfiehlt die Beschreibung für den Eintrag explizit Lösungen wie Web Application Firewalls (WAFs) und Runtime Application Self-Protection (RASP)-Produkte. Das wahrscheinliche Ergebnis ist, dass viele Entscheidungsträger die Abkürzung nehmen werden, eine WAF zu kaufen und ein Häkchen neben A7 auf der Top-10-Liste zu setzen.
Noch schlimmer, wie Timothy Morgan auf der OWASP Top 10 Mailingliste aufdeckte und wie in James Kettles Blogbeitrag weiter ausgeführt, scheint “Insufficient Attack Protection” einseitig von Contrast Security, einem RASP-Lösungsanbieter mit Interessenkonflikt, hinzugefügt worden zu sein. Jeff Williams, CTO von Contrast Security, hat seitdem auf die Anschuldigungen in einem Blogbeitrag reagiert.
Es gibt viele Vorteile, eine benutzerdefiniert konfigurierte WAF als Defense-in-Depth-Maßnahme zu verwenden, aber eine Empfehlung sollte darauf hinweisen, dass dies kein Allheilmittel ist, und dass es potenzielle Fallstricke gibt. Das Hinzufügen einer zusätzlichen Komponente wie einer WAF oder RASP zu Ihrer Systemarchitektur vergrößert auch Ihre Angriffsfläche. WAFs und RASPs filtern den gesamten Traffic Ihrer Webanwendung und suchen nach potenziellen Angriffsmustern, meist mit Hilfe von regulären Ausdrücken (da kommerzielle Angebote Black Boxes sind, gibt es keine Möglichkeit, sicher zu sein, wie sie genau funktionieren). Reguläre Ausdrücke können anfällig für Denial-of-Service-Angriffe sein. Die WAF- oder RASP-Software selbst kann auch Schwachstellen haben, die manchmal aus komplexen Interaktionen zwischen Komponenten resultieren. Ein aktuelles Beispiel ist Cloudflares “Cloudbleed”-Schwachstelle. WAFs können sicherlich auch umgangen werden - wir hatten einige interessante Ergebnisse mit HTTP-Multipart-Anfragen, aber das ist ein Thema für einen anderen Blogbeitrag. In der Empfehlung von RASP als Lösung wird nicht erwähnt, dass es nur für Java- und .NET-Webanwendungen funktioniert.
Es lohnt sich, einen Blick auf die Rohdaten des Top 10 2017 Data Call zu werfen. (Nebenbei bemerkt, Brian Glas hat eine exzellente Analyse der Daten durchgeführt und gezeigt, dass automatisierte Scanner und Menschen unterschiedliche Arten von Schwachstellen finden und eine Kombination aus beidem unverzichtbar ist.)
Die Statistiken identifizieren nicht nur XXE als eine sehr verbreitete Schwachstelle, die einen Platz in den Top 10 verdient hätte, sie nennen auch “Insufficient Anti-Automation” viel häufiger als “Insufficient Attack Protection”. Dies weist uns in die Richtung der Lösung, die wir Entwicklern meiner Meinung nach zur Implementierung empfehlen sollten.
2. Angriffsdetektion mit Honeypots
Ähnlich wie wir Brute-Force-Angriffe gegen Logins bereits mit einem einfachen Zähler erkennen und kleine Turing-Tests namens CAPTCHAs verwenden, um das Spamming eines Formulars zu verhindern, können wir mit nur wenigen Zeilen zusätzlichem Code eine effektive Angriffsdetektion und -reaktion durchführen. Wir können sowohl automatisierte Angriffe von Web-Schwachstellen-Scanning-Tools wie PortSwigger Burp Suite oder OWASP ZAP als auch manuelle Angriffe direkt in unserer Webanwendung erkennen. Tatsächlich ist es der perfekte Ort dafür! Im Gegensatz zu einer WAF oder einem IDS, die die Anwendungslogik nicht kennen und manchmal legitime Benutzer blockieren, ist die Erkennung von Angriffen in unserer Anwendung selbst frei von False Positives.
Alle unten beschriebenen Methoden zur Angriffsdetektion wurden ausführlich in Kapitel 3 von Ryan Barnetts und Jeremiah Grossmans Buch “Web Application Defender’s Cookbook: Battling Hackers and Protecting Users” behandelt, das ich sehr empfehle. Während das Buch Angriffsdetektion und -reaktion mit der mod_security Web Application Firewall löst, benötigen Sie keine WAF. Stattdessen werden wir betrachten, wie man dies innerhalb unserer Web-App macht.
Die Idee ist einfach: Wir legen Honeypots in unserer Anwendung aus, wie z.B. einen gefälschten Parameter ohne tatsächliche Funktionalität. Wenn der Parameterwert manipuliert wird, können wir sicher sein, dass es sich um einen Angriff handelt. Wir können zur Reaktionsphase übergehen und entscheiden, wie wir mit dem Angriff umgehen.
Der Honeypot wird automatisch von Web-Schwachstellen-Scannern aufgegriffen, die versuchen, jeden Parameter zu modifizieren. Um menschliche Angreifer weiter anzulocken, können wir dem Parameter einen verlockenden Namen wie "isAdmin=0" geben. Spüren Sie nicht auch den Drang herauszufinden, was passiert, wenn Sie das in isAdmin=1 ändern?
Im Gegensatz zu einer WAF/RASP müssen wir die Art des Angriffs nicht identifizieren (Ist es SQL Injection? Ist es Cross-Site Scripting?). Es reicht zu wissen, dass es mit Sicherheit ein Angriff ist und ihn dann zu blockieren. Wir müssen den Parameterwert nicht interpretieren oder reguläre Ausdrücke darauf anwenden. Wir prüfen einfach, ob er geändert wurde: if($isAdmin != 0). Dieser einfache Ansatz beseitigt den Großteil der Komplexität des Angriffsschutzes. Führen Sie dennoch unbedingt ein Code-Review Ihres Angriffsschutz-Codes durch, nachdem Sie ihn implementiert haben.
Aktiver Angriffsschutz bedeutet, dass Sie Penetrationstests gegen einen speziell bereitgestellten Testserver durchführen sollten, bei dem der Schutz ausgeschaltet ist. Sie wollen nicht Ihr ganzes Geld dafür ausgeben, dass PenTester versuchen, Ihren Schutz zu umgehen, Sie wollen, dass sie sich darauf konzentrieren, die eigentlichen Schwachstellen hinter den Schutzmaßnahmen zu finden. Wenn Sie ein Bug-Bounty-Programm betreiben, schalten Sie Ihren Angriffsschutz nicht aus.
Lassen Sie uns einige geeignete Orte für Honeypots durchgehen:
2.1 Gefälschte Formularfelder
Versteckte Formularfelder sind der perfekte Ort für einen Honeypot. Sie sind explizit nicht dazu gedacht, vom Benutzer geändert zu werden, daher deutet jede Änderung auf eine Manipulation hin. Der Name für das Honeypot-Formularfeld sollte so gewählt werden, dass er sich in die Funktionalität des Formulars einfügt. Alternativ kann ein plausibler generischer Name wie "debug", "context" oder "resource" verwendet werden.
<input type="hidden" name="debug" value="0"/>
Jede POST-Anfrage mit einem Wert ungleich Null für den debug-Parameter kann als bösartig angesehen werden und sollte mit einer oder mehreren der im Kapitel “Angriffsreaktion” unten beschriebenen Reaktionsmaßnahmen behandelt werden.
Für Single-Page-Anwendungen und Web-APIs können Sie ähnlich eine nicht-funktionale Parameter/Wert-Kombination hinzufügen. Achten Sie darauf, die wahre Honeypot-Funktionalität des Parameters nicht in öffentlich zugänglicher API-Dokumentation preiszugeben.
2.2 Gefälschte Cookies
Cookies sind ein weiterer sehr effektiver Ort für einen Honeypot. Viele Webanwendungen verwenden Tracking-Cookies mit kryptischen Werten, Base64-codierten Strings oder Hash-Werten. Das Verstecken eines gefälschten Cookies unter diesen ist einfach. Setzen Sie das Honeypot-Cookie zur gleichen Zeit, zu der Sie das Session-Cookie oder ein anderes gültiges Cookie setzen.
Burp Suite Professional und OWASP ZAP werden automatisch versuchen, Cookie-Parameterwerte zu manipulieren. Um menschliche Angreifer weiter anzulocken, verwenden Sie so etwas wie env=prod (was auf eine Produktionsumgebungseinstellung hindeutet, die in staging oder dev geändert werden könnte) oder debug=false:
Set-Cookie: env=prod; path=/; domain=yoursite.com; httponly
Alle eingehenden Anfragen mit einem anderen Cookie-Wert als prod können als Angriff gewertet werden.
2.3 Gefälschte HTML-Kommentare
Das Auskommentieren von altem HTML-Code ist eine schlechte Entwicklungspraxis, die noch nicht ganz ausgestorben ist. Sowohl Burps als auch OWASP ZAPs Spider-Module werden Links in HTML-Kommentaren aufgreifen und ihnen folgen (solange sie dem aktuellen Projektumfang entsprechen). Wählen Sie einen Link auf Ihrer Seite und fügen Sie daneben einen HTML-Kommentar hinzu, der auf eine link_old oder link.bak Seite verweist:
<!-- old link: <a href="page1_old">page1</a> -->
Jeder Besuch der Seite kann als von automatisierten Web-Schwachstellen-Scannern oder menschlichen Angreifern stammend angenommen werden.
2.4 Gefälschte robots.txt-Einträge
Eines der ersten Dinge, die ein PenTester während der Enumerierungsphase eines Webanwendungstests prüft, ist die robots.txt-Datei. Allzu oft folgen Admins der Logik “wir wollen nicht, dass interne Teile der App bei Google auftauchen, also blockieren wir sie mit robots.txt”. Gleichzeitig wird der exakte Pfad jedem offengelegt, der sich die Datei ansieht. Wir haben Disallow:-Einträge in robots.txt gesehen, die uns zu Session-Verzeichnissen, alten Backup-Versionen von Apps, Verzeichnissen mit interner API-Dokumentation und vielem mehr führten.
Fügen Sie einen scheinbar legitimen Eintrag zu Ihrer robots.txt hinzu, wie z.B.:
Disallow: /appname.bak/
Jeder, der versucht, auf diesen Pfad auf dem Webserver zuzugreifen, ist zumindest verdächtig, obwohl nicht alle Zugriffe auf diesen Honeypot gezielte Angriffe sein werden. Dennoch können Sie es sich wahrscheinlich leisten, Scraper und unseriöse Indexierungs-Bots zu blockieren, die die robots.txt ignorieren. Bevor Sie einen gefälschten robots.txt-Eintrag implementieren, bedenken Sie das Risiko, legitime Benutzer auszusperren, falls der Link in der robots.txt in einer Phishing-E-Mail verwendet wird.
3. Angriffsreaktion
Die Reaktion auf einen Angriff fällt im Allgemeinen in eine von zwei Kategorien: eine passive Reaktion, die für den Angreifer unsichtbar ist, und eine aktive Reaktion. In den meisten Fällen werden Sie den Angriff einfach blockieren & protokollieren wollen.
Seien Sie sich bewusst, dass jede Reaktionsfunktionalität, die Sie hinzufügen möchten, sicher implementiert werden muss. Versuchen Sie, es so einfach wie möglich zu halten. Wenn Ihre Reaktionsmaßnahme das Einbinden zusätzlicher Bibliotheken erfordert, ziehen Sie eine einfachere Reaktionsmaßnahme in Betracht oder führen Sie eine Sicherheitsüberprüfung der Bibliotheken durch. Führen Sie vor der Implementierung von Reaktionsmaßnahmen, die Angreifer dauerhaft blockieren, eine Risikoanalyse bezüglich der Auswirkungen einer versehentlichen Blockierung legitimer Benutzer durch und haben Sie einen Plan, wie Entsperrungen gehandhabt werden.
Ideen für Reaktionsmaßnahmen sind inspiriert vom AppSensor-Projekt von OWASP, einem Java-basierten Framework für Web-Intrusion-Detection und -Response. AppSensor bietet sogar Funktionalität für eine intrusive Reaktion, die hier nicht behandelt wird. Reaktionsaktionen wie das Abschalten einer Funktionalität werden nicht empfohlen, da sie nur ein Denial-of-Service-Angriff sind, der darauf wartet, zu passieren.
3.1 Aktive Reaktion
3.1.1 Angriff blockieren
Normalerweise wollen Sie Angriffe direkt blockieren, indem Sie die Anfrage verwerfen und eines oder mehrere der folgenden Dinge tun:
- Den aktuellen Geschäftsprozess beenden (z.B. Bestellvorgang abbrechen)
- Den Benutzer ausloggen
- Auf Fehlerseite umleiten
- Auf Startseite umleiten
3.1.2 Rate Limit Attack
Führen Sie künstlich verlängerte Antwortzeiten für Anfragen ein. Wie bei fehlgeschlagenen Anmeldeversuchen üblich, können Sie die Verzögerung mit jeder erkannten Angriffsanfrage weiter erhöhen.
3.1.3 Kontosperrung
Für eine dauerhaftere Maßnahme kann das Benutzerkonto deaktiviert werden. Dies kann dauerhaft oder vorübergehend für ein erstes Vergehen geschehen. Stellen Sie sicher, dass auch alle mit dem Konto verbundenen Sitzungen beendet werden.
Falls gewünscht, kann die IP des Benutzers für einen bestimmten Zeitraum blockiert werden. Dies sollte durch Weitergabe der Informationen an eine Firewall oder fail2ban geschehen. Ein übliches fail2ban-Setup besteht darin, einen speziell konfigurierten HTTP-Fehlercode in Ihrer Webanwendung zurückzugeben, wie z.B. 432, und fail2ban Ihre Webserver-Logs auf diesen Code überwachen zu lassen.
3.2 Passive Reaktion
3.2.1 Admin-Benachrichtigung
Die häufigste passive Reaktion besteht darin, eine Warnung per E-Mail, SMS, Slack oder Instant Messaging an einen Administrator oder ein Incident-Response-Team zu senden. Seien Sie vorsichtig, welche Art von Details Sie in die Warnung aufnehmen, abhängig davon, wie sicher der Kommunikationskanal ist.
3.2.2 Systembenachrichtigung
Senden Sie eine Warnung an Ihre anderen Sicherheitssysteme wie ein SIEM (Security Information and Event Management), IDS/IPS, Firewall, WAF, Load Balancer oder Log-Management-System wie Splunk oder ELK. IPS und Firewalls können die Warnung nutzen, um aktive Reaktionsmaßnahmen wie das Blockieren der betreffenden IP zu ergreifen.
3.2.3 Protokollierung ändern
Wenn Sie sich entscheiden, dem Angreifer weiterhin Zugriff auf die Anwendung zu gewähren, wäre eine erhöhte, fokussierte Protokollierung seiner Aktivitäten eine sehr ratsame zusätzliche Reaktionsmaßnahme. Zum Beispiel könnten Sie beginnen, den tatsächlichen Inhalt seiner POST-Anfragen in einem speziellen Vorfall-Protokoll zu speichern. Wie bei jeder Protokollierung, überprüfen Sie doppelt, ob die Protokolldaten ordnungsgemäß bereinigt sind, um Angriffe gegen den Log-Viewer zu verhindern.
3.2.4 Kontofunktionalität einschränken
Auf die gleiche Weise können Sie, wenn Sie den Angriff fortsetzen lassen, die Kontofunktionalität einschränken. Dateiuploads können deaktiviert oder in der Größe stark begrenzt werden, CAPTCHAs können für Übermittlungsformulare aktiviert werden, Aktionen wie Bestellungen können als wahrscheinlich betrügerisch gekennzeichnet werden usw.
3.2.5 Umleitung zum Honeypot/Tarpit
Leiten Sie alle Angreiferanfragen an ein speziell vorbereitetes Honeypot-System weiter, das die echte Webanwendung nachahmt, und überwachen Sie ihr Verhalten, um mehr über ihre Angriffsvektoren zu erfahren. Dies wäre eine ideal geeignete Reaktionsmaßnahme, wenn menschliche Angreifer identifiziert werden, z.B. durch Parameterwerte, die ein Mensch wahrscheinlich eingeben würde (unser "env=prod" Beispiel).
Der Honeypot könnte auch automatisierte Scanning-Tools mit endlosen Link-/Redirect-Ketten unter Verwendung eines Web-Tarpits wie TarPyt oder WebLabyrinth in die Falle locken.
4. Weiterführend: Honeytokens
Fertig mit dem Hinzufügen von Honeypots zu Ihrer Web-App? Der nächste Schritt in der Detektion wäre die Fähigkeit, einen erfolgreichen Angreifer aktiv zu erkennen, der sich mit Ihren gestohlenen Assets davonmacht.
Wir können unser eigenes Data Loss Prevention (DLP) unter Verwendung sogenannter Honeytokens aufbauen. Für jeden Satz sensibler Datensätze fügen wir einen gefälschten Eintrag hinzu. Fügen Sie zum Beispiel eine zusätzliche Zeile in der Benutzertabelle mit einem gefälschten Benutzer und einem sehr spezifischen Benutzernamen oder einer E-Mail hinzu. Wenn auf diesen Tabelleneintrag jemals in der Datenbank zugegriffen wird oder wenn jemand versucht, sich mit diesem Benutzernamen/dieser E-Mail anzumelden, können wir sicher sein, dass die Benutzertabelle kompromittiert wurde.
Ebenso können wir eine gefälschte Datei in einem Dateispeicher, ein gefälschtes unsichtbares Produkt in der Produkttabelle usw. hinzufügen. Die Erkennung kann in einer WAF oder einem IDS erfolgen. Es ist ein Konzept, das bis in die Zeit vor dem digitalen Zeitalter zurückreicht, als Enzyklopädien und Karten fiktive Einträge oder gefälschte Straßen verwendeten, um Nachahmer erkennen zu können.
Ich hoffe, dieser Blogbeitrag hat aufgezeigt, wie Sie Angriffsdetektion und -reaktion in Ihrer Webanwendung mit nur wenigen Zeilen Code durchführen können, bevor Sie viel Geld für WAFs und RASPs ausgeben. So interpretiert, wäre eine OWASP Top 10 Empfehlung für Entwickler, Angriffsschutz in ihren Apps zu implementieren, eine wertvolle Ergänzung.
Lesen Sie über weitere interessante Themen in unserem Blog.