Apache Killer (CVE-2011-3192): So wirkt der Angriff – und so testen Sie ihn

Ein winziger Eingabe-Splitter schwillt zu aufgeblähten Speicherblöcken an – die Speicherverstärkung von Apache Killer

· 14 Min. Lesezeit

Apache Killer gehört zu den wenigen Denial-of-Service-Angriffen, die fast ohne Datenverkehr auskommen. Eine einzige kleine GET-Anfrage mit einem Range-Header, der Dutzende überlappende Ausschnitte derselben Datei verlangt, bringt einen anfälligen Apache HTTP Server dazu, den Antwort-Body immer wieder neu im Speicher anzulegen, bis dem Prozess der Platz ausgeht. Die Schwachstelle ist alt, und sie hat einen Namen und eine Nummer: CVE-2011-3192, veröffentlicht im August 2011.

Genau dieses Alter macht sie für ein Testprogramm interessant. In jedem aktuellen Apache-Build ist die Lücke geschlossen. Die Frage lautet deshalb nicht mehr «Kann mich das treffen?», sondern «Läuft überall wirklich das, was ich glaube – auch auf der vergessenen Appliance und auf der Hersteller-Box, die seit Jahren niemand neu aufgesetzt hat?». Apache Killer beantwortet sie sauber, denn die Antwort des Servers ist bereits das Ergebnis.

Das Wichtigste in Kürze

  • Der Angriff zielt auf den Speicher, nicht auf die Bandbreite. Der Schaden entsteht dadurch, dass sich Heap- und Resident-Speicher je Anfrage vervielfachen, und nicht durch Gigabit oder Anfragen pro Sekunde. Deshalb genügt eine niedrige Anfragerate, um einen ungepatchten Server zu erschöpfen.
  • Das Mittel ist ein erzwungener Range-Header. Jede Anfrage verlangt viele überlappende Byte-Bereiche einer einzigen Datei, und ein anfälliger Server legt für jeden Bereich eine eigene Kopie des Antwort-Bodys an.
  • Die betroffenen Versionen sind genau bekannt. Apache HTTP Server 1.3.x, 2.0.x bis 2.0.64 und 2.2.x bis 2.2.19. Behoben wurde die Lücke am 30. August 2011 mit 2.2.20.
  • Das ist der eine Angriff dieser Reihe, den eine WAF wirklich abfängt. Das Muster der überlappenden Bereiche ist eine feste Signatur und nicht bloss Verkehr, der legitim aussieht; eine passend konfigurierte Regel blockiert die Anfrage, bevor sie den Server erreicht.
  • Die Antwortkategorie ist der Befund. Wie Ihr Server auf eine einzige präparierte Anfrage reagiert, zeigt, ob Sie gepatcht sind, ob etwas weiter vorne die Anfrage abweist oder ob Sie angreifbar sind.

Dieser Beitrag gehört zu einer Reihe über die zehn Simulationstypen, die Obsidio durchführt, ein Beitrag je Angriff. Sie setzen an ganz unterschiedlichen Stellen an, und deshalb braucht ein Testprogramm Abdeckung über alle Kategorien statt Volumen in einer einzigen. Wie sie zusammenspielen und wie Sie einen ersten Durchlauf aufbauen, steht in unserem Leitfaden dazu, wie Sie Ihren DDoS-Schutz testen.

Die zehn Simulationstypen

Je ein Beitrag, gruppiert wie in der Plattform.

Angriffe auf der Anwendungsschicht (L7)

Langsame Angriffe

Verbindungserschöpfung

Protokollspezifisch & skriptgesteuert

Was ein Apache-Killer-Angriff tatsächlich macht

Den HTTP-Header Range gibt es aus gutem Grund. Er erlaubt einem Client, nur einen Teil einer Datei anzufordern statt der ganzen; so setzt ein abgebrochener Download wieder an, und so holt ein Videoplayer genau das Segment, das er als Nächstes abspielt. Eine wohlgeformte Anfrage lautet Range: bytes=0-1023 und erhält das erste Kilobyte zurück, und die Spezifikation erlaubt einem Client sogar, mehrere Bereiche auf einmal zu verlangen.

Genau diesen letzten Punkt missbraucht Apache Killer. Der Angriff sendet eine Anfrage, deren Range-Header viele überlappende Byte-Bereiche derselben Datei auflistet, etwa bytes=0-1,5-1,5-2,5-3, und so weiter. Ein anfälliger Server nimmt die Liste wörtlich und legt für jeden Bereich einen eigenen Puffer an. Weil sich die Bereiche überlappen und wiederholen, entsteht schon aus einer winzigen Datei ein Vielfaches davon im Speicher. Das Senden der Anfrage kostet den Angreifer fast nichts; das Zusammensetzen der Antwort kostet den Server ein Vielfaches der Dateigrösse an Heap- und Resident-Speicher.

Deshalb verhält sich der Angriff so anders als ein Flood. Er setzt nicht auf Bandbreite oder Anfragerate, sondern auf Speicher: Eine Handvoll solcher Anfragen parallel treibt einen ungepatchten httpd-Prozess in die Erschöpfung, während die Verkehrskurve kaum ausschlägt.

Anschaulich gesagt: Sie verlangen von einer Bibliothekarin eine einzige Seite, aber in fünfzig Stücken, die sich fast alle überlappen. Um Ihre Bestellung zu erfüllen, kopiert sie die Seite fünfzig Mal. Geben Sie ein paar solche Bestellungen gleichzeitig auf, geht ihr das Papier aus – und gefragt haben Sie immer nur nach einer einzigen Seite.

Welche Ihrer Schutzmassnahmen das hätte abfangen sollen

Es lohnt sich, die ganze Kette abzugehen, die eine Anfrage durchläuft, denn die Antwort fällt hier anders aus als sonst in dieser Reihe. Drei Bereiche zählen: was vorgelagert ist, was die durchgelassene Last auffängt, und ob Ihnen überhaupt jemand meldet, dass etwas passiert ist.

Zone 1

Was fängt sie auf?

  • DDoS-Schutz und Scrubbing. Reagieren erst auf einen Anstieg im Datenverkehr. Den gibt es bei diesem Angriff nicht, also fehlt der Auslöser.
  • Firewall und WAF. Die Ausnahme dieser Reihe, und das gehört deutlich gesagt. Das Muster der überlappenden Bereiche ist eine bekannte Signatur und nicht Verkehr, der bloss legitim aussieht; eine passend konfigurierte Regel greift hier also tatsächlich und blockiert die Anfrage. Das gilt nur, wenn die Regel vorhanden und aktuell ist – in vielen Installationen fehlt sie ganz.
  • Rate Limiting. Zählt Anfragen. Hier kommen viel zu wenige zusammen, um einen Schwellenwert zu erreichen, denn die Vervielfachung steckt in jeder einzelnen Anfrage und nicht in ihrer Zahl.
  • Bot-Erkennung und Challenges. Es ist ein einfaches GET ohne Seitenaufbau und ohne Session, die sich auswerten liesse. Eine Challenge findet keinen Ansatzpunkt.
  • CDN oder vorgelagerter Cache. Ein CDN, das Bereiche normalisiert oder zusammenfasst, schirmt den Ursprungsserver ab; eines, das den Range-Header unverändert weiterreicht, nicht. Prüfen Sie, was Ihres tut.

Zone 2

Was bekommt die Last ab?

  • Load Balancer oder Reverse Proxy. Fängt den Angriff ab, wenn er masslose Bereichslisten zusammenfasst oder abweist, bevor er sie weiterleitet. Prüfen Sie, ob Ihrer das tut, statt den Header einfach durchzureichen.
  • Verbindungsschicht. Nicht die Bruchstelle. Der Angriff nutzt wenige Verbindungen mehrfach und richtet die Last auf den Speicher, nicht auf Sockets.
  • Webserver. Hier entsteht der Schaden – und nur bei einem anfälligen Apache-Build. Mit jeder solchen Anfrage wächst der Resident-Speicher, bis der Prozess nichts mehr anfordern kann.
  • Anwendung und Datenbank. Werden nie erreicht. Der Antwort-Body entsteht in der Byte-Range-Verarbeitung des Servers, noch bevor irgendeine Anwendungslogik läuft.
  • Auto-Scaling. Richtet sich nach Anfragerate oder CPU; beides steigt nicht. Der Speicherverbrauch klettert unauffällig auf einem einzelnen Host, eine ratenbasierte Regel skaliert deshalb nie.

Zone 3

Würden Sie davon erfahren?

  • Dashboards. Die Anfragen pro Sekunde sehen normal aus, sogar niedrig. Die Last liegt im Speicher, und dorthin schauen die meisten Verkehrs-Dashboards nicht.
  • Eine Prüfung von ausserhalb Ihres Netzes. Das mit Abstand nützlichste Signal. Die Antwort auf eine einzige präparierte Anfrage sagt Ihnen unmissverständlich, ob Sie gepatcht sind.
  • Logging und Ihr SIEM. Diese Anfragen werden abgeschlossen; anders als bei einem langsamen Angriff hinterlassen sie also Einträge im Access-Log. Auffallen wird ein ungewöhnlicher Range-Header aber niemandem, solange keine Regel dafür geschrieben wurde.
  • Alarmierung. Nichts überschreitet einen Schwellenwert für Anfragerate oder Bandbreite.
  • Pikettdienst. Geht dem Prozess der Speicher aus, bietet das Host-Monitoring vielleicht jemanden wegen eines Absturzes oder Neustarts auf – auch wenn niemand den Angriff dahinter erkannt hat.

Violett markiert, was sich nur mit einem Test auf Ihrer eigenen Infrastruktur klären lässt. Alles Übrige folgt aus der Funktionsweise des Angriffs und nicht daraus, wie sorgfältig Ihr Team konfiguriert hat.

Das Bild fällt hier weniger düster aus als bei den meisten Angriffen dieser Reihe, und das gehört nüchtern festgehalten: Ein gepatchter Server und eine passende Regel am Netzrand stoppen den Angriff wirklich. Das Risiko besteht nicht darin, dass er unaufhaltsam wäre, sondern darin, dass Sie sich überall gepatcht glauben, ohne es je belegt zu haben.

Die eine Anfrage, die zeigt, ob Sie gepatcht sind

Apache Killer lässt sich ungewöhnlich sauber diagnostizieren. Sie müssen nichts überlasten, um Ihren Stand zu kennen: Senden Sie die präparierte Anfrage und lesen Sie die Antwort, denn die Antwortkategorie entspricht direkt Ihrem Zustand.

Ein gepatchter Server spielt nicht mit. Erhält er eine Liste überlappender Bereiche, deren Aufwand grösser wäre als die Datei selbst, ignoriert er sie und liefert die vollständige Datei mit einer normalen 200-Antwort, oder er weist die Anfrage direkt ab. Ein ungepatchter Server tut das Gefährliche: Er antwortet mit einer Multipart-Range-Antwort, die je angefordertem Bereich einen Teil enthält – die Vervielfachung in Aktion. Eine Ablehnung durch einen vorgelagerten Proxy oder einen gehärteten Stack, der den übergrossen Header abweist, bevor er den Ursprungsserver erreicht, ist ein dritter und genauso aussagekräftiger Ausgang. Jeder davon ist eine andere, klar lesbare Antwort auf dieselbe Frage.

In der Obsidio-Simulation steuern zwei Parameter das Verhalten. rangeCount ist der Regler für die Vervielfachung: Er legt fest, wie viele überlappende Byte-Bereiche jede Anfrage enthält, und ein anfälliger Server legt je Eintrag eine Kopie der Antwort an. Der Standardwert liegt bewusst milde bei 10 – genug, um den Effekt zu zeigen, ohne etwas zu belasten. Erhöhen Sie ihn in Schritten, statt gleich auf das Maximum zu gehen, und beobachten Sie, welche Antwortkategorie jeweils zurückkommt. Ein dreistelliger Wert setzt einen ungepatchten Server stark unter Druck; einen sehr hohen Wert weist ein moderner Stack womöglich schlicht ab, was für sich genommen ebenfalls ein nützliches Signal ist. Der zweite Parameter, parallelRequestsPerWorker, steht standardmässig auf 20 und bestimmt, wie viele Anfragen gleichzeitig laufen; er vervielfacht die Speicherkopien, die gleichzeitig unterwegs sind, ohne die Vervielfachung je Anfrage zu verändern.

Ein Detail ist für das Lesen der Ergebnisse wichtig: Der Range-Header wird aus rangeCount berechnet und jeder Anfrage zwingend mitgegeben. Überschreiben lässt er sich nicht, denn er ist der Angriff. Eigene Header kommen zusätzlich hinzu.

Wie Sie sich gegen Apache Killer schützen

Die Verteidigung beginnt bei der Versionsnummer und arbeitet sich von dort nach aussen. Jede Schicht lässt sich überprüfen, und das ist der nützliche Teil.

  • Zuerst und immer: der Patch-Stand. Die Korrektur für CVE-2011-3192 erschien am 30. August 2011 mit Apache HTTP Server 2.2.20. Der Changelog-Eintrag ist präzise: Der Server verarbeitet Byte-Range-Anfragen nun mit weniger Speicher, und wenn die Summe aller Bereiche einer Anfrage grösser ist als die Originaldatei, ignoriert er die Bereiche und liefert die vollständige Datei («if the sum of all ranges in a request is larger than the original file, ignore the ranges and send the complete file»). Ein Nachtrag in 2.2.21 korrigierte eine Regression, die die erste Korrektur eingeführt hatte. Jede aktuelle Apache-Version enthält all das längst; die Arbeit besteht also darin, zu bestätigen, dass wirklich jeder Server aktuell ist, Appliances und vom Hersteller gelieferte Instanzen eingeschlossen.
  • Grenzwerte für die Bereichsverarbeitung. Aktuelle Apache-Versionen bieten drei Direktiven, die masslose Bereichslisten direkt begrenzen. MaxRanges beschränkt die Zahl der Bereiche, ab der der Server stattdessen die vollständige Ressource ausliefert, Standardwert 200. MaxRangeOverlaps begrenzt überlappende Bereiche, MaxRangeReversals begrenzt Rückwärtssprünge in der Reihenfolge, beide mit Standardwert 20. Alle drei kamen mit der Entwicklungslinie 2.3.15 und stecken in aktuellen stabilen Builds. Überschreitet eine Anfrage ein Limit, sendet der Server die ganze Datei, statt die Bereiche zu bedienen – damit entfällt die Vervielfachung.
  • Eine passend konfigurierte WAF-Regel. Weil das Muster der überlappenden Bereiche eine feste Signatur ist, kann eine Regel, die einen missbräuchlichen Range-Header erkennt, die Anfrage blockieren, bevor sie den Ursprungsserver erreicht. Genau das macht Apache Killer zur Ausnahme dieser Reihe. Auch auf gepatchten Servern lohnt sie sich als zweite Linie, sie ist aber nur so gut, wie sie aktuell ist.
  • Zusammenfassen am Proxy oder CDN. Die HTTP-Spezifikation hält selbst fest, dass ein Server Bereichsanfragen ignorieren, zusammenfassen oder ablehnen darf, wenn sie mehr als zwei überlappende Bereiche oder viele kleine Bereiche in falscher Reihenfolge verlangen, weil das auf einen fehlerhaften Client oder einen absichtlichen Denial-of-Service-Versuch hindeutet. Ein Proxy oder CDN, der das für Sie übernimmt, schirmt den Ursprungsserver ab, sofern dieser nicht direkt erreichbar ist.

Jede dieser Massnahmen ist irgendwo eine Einstellung oder eine Versionsangabe. Das heisst: Jede kann veraltet sein, auf einem Host fehlen oder durch eine Änderung überschrieben worden sein, die niemand nachgeprüft hat.

Was Sie selbst prüfen können und was dabei offen bleibt

Apache Killer ist der eine Angriff dieser Reihe, bei dem eine Selbstprüfung wirklich viel bringt. Zwei Prüfungen können Sie heute durchführen:

Version und Konfiguration lesen. Stellen Sie auf jedem Host fest, welcher Apache-Build läuft, und prüfen Sie, ob die Direktiven zur Bereichsverarbeitung gesetzt sind. Für die Maschine, die Sie angesehen haben, wissen Sie damit: Die Einstellung existiert, und die Version ist aktuell.

Eine Anfrage an das Staging-System senden und die Antwort lesen, mit Freigabe durch das Change-Management und nur auf Infrastruktur, die Ihnen gehört. Der Befund steckt in der Antwort selbst und nicht darin, ob der Server umgefallen ist; den tatsächlichen Stand dieses einen Endpunkts kennen Sie also sofort.

Die Falle liegt nicht darin, dass die Selbstprüfung Sie über den geprüften Endpunkt täuscht, sondern in dem, was eine einzelne Quelle nicht sehen kann. Eine Anfrage von einer einzelnen Maschine sagt nichts über die Endpunkte, an die Sie nicht gedacht haben, und das Risiko tragen genau die Vergessenen: die alte Appliance, die nie neu aufgesetzte Hersteller-Box. Sie sagt auch nichts darüber, ob während eines längeren Durchlaufs jemand den steigenden Speicherverbrauch bemerken würde. Eine einzelne Anfrage beantwortet die Frage nach der Version. Sie beantwortet weder die Frage nach der Abdeckung noch die nach der Erkennung, und das sind die beiden, die ein ernsthaftes Programm schliessen muss.

Wie Obsidio das testet

Obsidio führt Apache Killer als kontrollierte, autorisierte Simulation gegen Infrastruktur durch, die Ihnen gehört. Die Domain-Inhaberschaft wird über einen DNS-TXT-Eintrag geprüft, bevor überhaupt Datenverkehr fliesst. Die Durchläufe steigern sich stufenweise, beginnend beim milden Standardwert für die Bereichszahl, und jeder Durchlauf lässt sich im laufenden Betrieb abbrechen. Sie legen Bereichszahl und Parallelität fest und beobachten, wie jeder Endpunkt antwortet, während der Druck steigt. Weil die Last von über 100’000 weltweit verteilten echten Geräten kommt und nicht von einer Handvoll Instanzen im Rechenzentrum, wird Ihre Umgebung so abgeklopft, wie es ein echter Angreifer täte, und nicht aus einer einzelnen vorhersehbaren Quelle, die Ihre Filter mühelos erwischen würden.

Zu beobachten ist die Antwortkategorie, nicht die Kurve der Anfragerate; die bleibt niedrig, auch während der Angriff wirkt. Entscheidend ist die Mischung der Antworten: Eine saubere Antwort mit der vollständigen Datei oder eine Ablehnung heisst, dieser Endpunkt hält. Eine Multipart-Range-Antwort heisst, er vervielfacht und ist angreifbar. Wie sich diese Mischung verschiebt, während die Bereichszahl steigt, ist der ganze Zweck des Durchlaufs.

Was ein Test messen kann, hat eine klare Grenze. Obsidio misst von aussen die Antwortkategorie und das Verhalten am Netzrand, weil beides von der Client-Seite der Verbindung aus sichtbar ist. Ob der Resident-Speicher auf dem Host tatsächlich gestiegen ist, ob Ihr SIEM die Serie von Range-Anfragen aufgezeichnet hat und ob jemand aufgeboten wurde, als ein Prozess neu startete: Diese Antworten stehen nur auf Ihren eigenen Konsolen. Lassen Sie sie während des Zeitfensters von jemandem beobachten, damit sich das innere und das äussere Bild zu einem Befund zusammenfügen.

Stärke wird bewiesen, nicht versprochen. Apache Killer prüft nicht Ihre Bandbreite. Er prüft, ob die Version, die Sie zu betreiben glauben, auch die Version ist, die die Anfrage beantwortet.

Wo das in ein Testprogramm passt

Apache Killer gehört zur Gruppe der Angriffe auf die Anwendungsschicht, zusammen mit HTTP-Flood, GoldenEye und Browser-Flood, ist dort aber der Sonderfall. Die Floods wirken über Volumen und treffen die Kapazität der Anfrageverarbeitung. Apache Killer wirkt über einen bestimmten Implementierungsfehler und trifft den Speicher, praktisch ohne Volumen. Ein Programm, das nur Floods fährt, misst, wie viel Verkehr Ihr Stack aushält, stellt aber nie die Frage nach Version und Abdeckung, die dieser Angriff beantwortet. Diese ganze Klasse von Angriffsfläche bleibt damit ungeprüft.

Für regulierte Institute muss der Test zudem eine Spur hinterlassen. Obsidio erstellt kryptografisch attestierte, manipulationssichere Berichte, die FINMA, DORA und NIS2 zugeordnet sind und in Trusted Execution Environments erzeugt werden. Das Ergebnis eines Durchlaufs ist damit ein Beleg, den Sie ablegen können, und kein Screenshot, für den Sie sich verbürgen müssen. Bei einem Angriff, dessen ganzer Befund darin besteht, welcher Ihrer Server wie geantwortet hat, ist ein überprüfbarer Nachweis genau dieser Antworten viel wert.

Um eine autorisierte Apache-Killer-Simulation gegen Ihre eigene Infrastruktur aufzusetzen, sehen Sie sich die Obsidio-Plattform an oder sprechen Sie mit dem Team. Unabhängig, neutral, überprüfbar: Resilienz, die Sie belegen können.

← Zurück zum Blog