Drahtlose Netzwerke sind überall: Zu Hause, im Café und in der Firma. Im Gegensatz zu Kabelnetzen verliert der Admin bei WLANs allerdings schnell die ... (mehr)

Proof-of-Concept-Angriff

Für das Verständnis des Beispiels aus Listing 1 ist die Kenntnis einiger Maschineninstruktionen nützlich:

Listing 1

Asus RT-AC66U Roip Chain

 

  • LUI – Load upper immediate: Der konstante Wert wird 16 Bit nach links verschoben und in einem Register gespeichert. Die unteren 16 Bit sind Nullen.
  • ORI – Bitwise OR immediate: Bitweises Oder eines Registers mit einer Konstanten. Das Resultat wird in einem Register abgelegt.
  • SW – Store word: Speichert den Inhalt des angegebenen Registers an der angegebenen Adresse.
  • ADDI – Add immediate: Addiert den Registerinhalt mit einer vorzeichenbehafteten Konstanten und speichert das Resultat in einem Register.
  • JALR – Jump and link: Springt zur berechneten Adresse.

Im Fall des Asus RT-AC66U ermöglichte die mangelhafte Überprüfung von Grenzen im Code und die Unmöglichkeit, Netzwerk-Services abzuschalten, den im folgenden skizzierten Angriff, der es erlaubt, beliebigen Code mit den Rechten des Eigentümers der Applikation auszuführen, was normalerweise Root ist.

Der Asus RT-AC66U führt mit oder ohne angesteckten USB-Speicher einen ACSD-Service an Port TCP/5916 aus. Dieser Service läuft per Default. Er lässt sich nicht deaktivieren. Der ACSD-Service ist durch einen Buffer-Overflow während der Abarbeitung der Kommandoroutine angreifbar (CVE-2013-4659). Der Angreifer verbindet sich dazu mit dem ACSD-Service und übergibt ihm einen Kommandostring, der länger ist als die fest eingestellte Puffergröße. Damit wird der Call Stack und angrenzender Speicher überschrieben. Im Ergebnis kann vom Angreifer kontrollierter Code ausgeführt werden.

Die Attacke benutzt Return Oriented Programming (ROP), um die Randomisierung des Stacks zu umgehen und Cache-Inkohärenz zu vermeiden (Listing 1). Um einen kohärenten CPU-Daten-Cache zu erhalten, nutzt der Payload den Aufruf der Blocking Function »sleep()« . Das geschieht, indem zunächst im ersten Gadget der Wert 1 in das A0-Register geladen wird. Das Gadget 2 lädt dann die Adresse der Sleep-Funktion in das $T9-Register und schließt danach mit einem Sprung zu $T9 ab. Das wiederum bewirkt auf dem Zielsystem einen Context Switch und solche Context Switches flushen schließlich den Data Cache in das RAM. Als nächstes stellt Gadget 3 das Stackpointer-Register »sp« so ein, dass es nach Addition einer Konstanten auf den böswilligen Shellcode verweist. Schließlich kommt noch das Gadget 4 an die Reihe, dass den Programmablauf an die im Register $T9 gespeicherte Stelle verzweigen lässt, an der sich der böswillige Shellcode befindet. Dieser startet sodann mithilfe der Systemfunktion »system()« aus der Standard-C-Bibliothek einen nicht autorisierten Telnet-Server (Abbildung 5).

Abbildung 5: Der böswillige Shellcode, den die Beispielattacke ausführt.

In der gleichen Weise wie beim RT-AC66U konnten wir auch beim Asus RT-N56U beliebigen Code mit Root-Rechten ausführen. Hier war der Angriffspunkt ein immer laufender und nicht abschaltbarer HTTP-Server, der für mehrere Buffer-Overflows (CVE-2013-6343) während des Konfigurationsprozesses anfällig ist. Auch hier kann der Call Stack mit einer überlangen Kommandoeingabe überschrieben werden. Wieder wurden mehrere ROP-Gadgets verwendet, um den Stack  einzurichten und die Kommandoausführung auf gefährlichen Shellcode im Memory umzulenken. Im Zuge des Angriffs öffnet der angegriffene Router einen Netzwerk-Socket, verbindet sich mit Port TCP/31337 auf einer Maschine des Angreifers und führt dort eine Root-Shell aus. Anschließend kann der Angreifer direkt mit dem darunterliegenden Linux-System operieren (Listing 2).

Listing 2

Angriff auf Asus RT-N56U

 

Beständige Verwundbarkeiten

Die in diesem Artikel beschriebenen Verwundbarkeiten und andere, die im Zuge der Studie gefunden wurden, können vom Anwender nicht abgestellt werden. So lassen sich die ACSD- und HTTP-Services nicht abschalten. In anderen Fällen können Angriffe auf erforderliche Dienste dazu benutzt werden, um Dienste wieder einzuschalten, die der Anwender außer Betrieb genommen hatte. Damit ergibt sich eine unvermeidliche Unsicherheit dieser Devices. So bleiben sie ein ewiges Angriffsziel – zumindest so lange, bis der Hersteller eventuell einen Patch veröffentlicht.

Zur Beständigkeit der Schwachstellen kommt noch hinzu, dass alle untersuchten Router sehr benutzerunfreundliche Update-Prozesse bieten. Keiner der Router updatete sich automatisch, die meisten sendeten eine Nachricht an den Administrator, wenn Updates verfügbar waren, erforderten dann aber in einem mehrstufigen Prozess das nicht immer intuitive Flashen der Firmware. Für einen durchschnittlichen Anwender ist das Verfahren schwer verständlich, weswegen die Verwundbarkeiten in vielen Fällen auch dann bestehen bleiben, wenn der Hersteller einen Patch veröffentlicht.

Schließlich kann man im Falle eines kompromittierten Routers nichts weiter tun, als das Gerät außer Betrieb zu nehmen. Alles, was der Käufer unternehmen kann, reicht nicht, um ein erfolgreiches Firmware-Update zu garantieren. Hat der Angreifer erst einmal volle Kontrolle über den Router, kann er auch ein Update vereiteln.

Ähnliche Artikel

comments powered by Disqus

Artikel der Woche

Eigene Registry für Docker-Images

Wer selber Docker-Images herstellt, braucht auch eine eigene Registry. Diese gibt es ebenfalls als Docker-Image, aber nur mit eingeschränkter Funktionalität. Mit einem Auth-Server wird daraus ein brauchbares Repository für Images. (mehr)
Einmal pro Woche aktuelle News, kostenlose Artikel und nützliche ADMIN-Tipps.
Ich habe die Datenschutzerklärung gelesen und bin einverstanden.

Konfigurationsmanagement

Ich konfiguriere meine Server

  • von Hand
  • mit eigenen Skripts
  • mit Puppet
  • mit Ansible
  • mit Saltstack
  • mit Chef
  • mit CFengine
  • mit dem Nix-System
  • mit Containern
  • mit anderer Konfigurationsmanagement-Software

Ausgabe /2021