HWAddressSanitizer

Informationen zum Lesen von HWAAn-Abstürzen finden Sie unter HWAAn-Berichte verstehen!

Hardware-assisted AddressSanitizer (HWASan) ist ein Tool zur Erkennung von Speicherfehlern, ähnlich wie AddressSanitizer . HWASan verwendet im Vergleich zu ASan viel weniger RAM, wodurch es für die Bereinigung des gesamten Systems geeignet ist. HWASan ist nur auf Android 10 und höher und nur auf AArch64-Hardware verfügbar.

Obwohl HWAAn hauptsächlich für C/C++-Code nützlich ist, kann es auch beim Debuggen von Java-Code helfen, der Abstürze in C/C++ verursacht, das zum Implementieren von Java-Schnittstellen verwendet wird. Es ist hilfreich, weil es Speicherfehler abfängt, wenn sie auftreten, und Sie direkt auf den verantwortlichen Code hinweist.

Sie können vorgefertigte HWAAn-Images von ci.android.com auf unterstützte Pixel-Geräte flashen ( detaillierte Einrichtungsanweisungen ).

Im Vergleich zum klassischen ASan hat HWAAn:

  • Ähnlicher CPU-Overhead (~2x)
  • Overhead bei ähnlicher Codegröße (40 – 50 %)
  • Viel geringerer RAM-Overhead (10 % – 35 %)

HWASan erkennt die gleichen Fehler wie ASan:

  • Stack- und Heap-Pufferüberlauf/-unterlauf
  • Heap-Nutzung nach kostenlos
  • Stack-Verwendung außerhalb des Gültigkeitsbereichs
  • Doppelt frei/wild frei

Darüber hinaus erkennt HWAAn die Stack-Nutzung nach der Rückgabe.

HWASan (wie ASan) ist mit UBSan kompatibel, beide können gleichzeitig auf einem Ziel aktiviert werden.

Implementierungsdetails und Einschränkungen

HWASan basiert auf dem Speicher-Tagging -Ansatz, bei dem ein kleiner zufälliger Tag-Wert sowohl mit Zeigern als auch mit Bereichen von Speicheradressen verknüpft wird. Damit ein Speicherzugriff gültig ist, müssen Zeiger und Speicherkennzeichen übereinstimmen. HWASan stützt sich auf das ARMv8-Feature Top Byte Ignore (TBI), auch Virtual Address Tagging genannt, um das Pointer-Tag in den höchsten Bits der Adresse zu speichern.

Weitere Informationen zum Design von HWAAn finden Sie auf der Clang-Dokumentationsseite.

Per Design hat HWASan nicht die Redzones von ASan mit begrenzter Größe zur Erkennung von Überläufen oder die Quarantäne von ASan mit begrenzter Kapazität zur Erkennung der Nutzung nach der kostenlosen Nutzung. Aus diesem Grund kann HWASan einen Fehler erkennen, egal wie groß der Überlauf ist oder wie lange es her ist, dass der Speicher freigegeben wurde. Dies gibt HWAAn einen großen Vorteil gegenüber ASan.

HWAAn hat jedoch eine begrenzte Anzahl möglicher Tag-Werte (256), was bedeutet, dass eine Wahrscheinlichkeit von 0,4 % besteht, dass während einer Ausführung des Programms ein Fehler übersehen wird.

Anforderungen

Neuere Versionen (4.14+) des gemeinsamen Android-Kernels unterstützen HWAAn out-of-the-box. Die Android 10-spezifischen Zweige haben keine Unterstützung für HWAAn.

Userspace-Unterstützung für HWAAn ist ab Android 11 verfügbar.

Wenn Sie mit einem anderen Kernel arbeiten, erfordert HWASan, dass der Linux-Kernel markierte Zeiger in Systemaufrufargumenten akzeptiert. Die Unterstützung dafür wurde in den folgenden Upstream-Patchsets implementiert:

Wenn Sie mit einer benutzerdefinierten Toolchain erstellen, stellen Sie sicher, dass sie alles bis zum LLVM-Commit c336557f enthält .

Mit HWAsan

Verwenden Sie die folgenden Befehle, um die gesamte Plattform mit HWAAn zu erstellen:

lunch aosp_walleye-userdebug # (or any other product)
export SANITIZE_TARGET=hwaddress
m -j

Der Einfachheit halber können Sie die Einstellung SANITIZE_TARGET zu einer Produktdefinition hinzufügen, ähnlich wie bei aosp_coral_hwasan .

Für Benutzer, die mit AddressSanitizer vertraut sind, ist viel Build-Komplexität verschwunden:

  • make muss nicht zweimal ausgeführt werden.
  • Inkrementelle Builds funktionieren sofort.
  • Benutzerdaten müssen nicht geflasht werden.

Einige AddressSanitizer-Einschränkungen sind ebenfalls weg:

  • Statische ausführbare Dateien werden unterstützt.
  • Es ist in Ordnung, die Bereinigung eines anderen Ziels als libc zu überspringen. Anders als bei ASan gibt es keine Anforderung, dass, wenn eine Bibliothek bereinigt wird, auch alle ausführbaren Dateien, die sie verknüpfen, ebenfalls bereinigt werden müssen.

Das Umschalten zwischen HWAAn und regulären Images mit der gleichen (oder höheren) Build-Nummer kann frei erfolgen. Ein Abwischen des Geräts ist nicht erforderlich.

Um die Bereinigung eines Moduls zu überspringen, verwenden LOCAL_NOSANITIZE := hwaddress (Android.mk) oder sanitize: { hwaddress: false } (Android.bp).

Einzelne Ziele bereinigen

HWASan kann pro Ziel in einem regulären (nicht bereinigten) Build aktiviert werden, solange libc.so ebenfalls bereinigt wird. Fügen Sie hwaddress: true zum Sanitize-Block in "libc_defaults" in bionic/libc/Android.bp hinzu. Dann tun Sie dasselbe in dem Ziel, an dem Sie arbeiten.

Beachten Sie, dass das Bereinigen von libc das systemweite Taggen von Heap-Speicherzuweisungen sowie das Überprüfen der Tags für Speicheroperationen innerhalb libc.so . Dies kann Fehler sogar in Binärdateien abfangen, für die HWASan nicht aktiviert wurde, wenn der fehlerhafte Speicherzugriff in libc.so ist (z. pthread_mutex_unlock() auf einem delete() ed Mutex).

Es ist nicht erforderlich, Build-Dateien zu ändern, wenn die gesamte Plattform mit HWAAn erstellt wird.

Flashstation

Zu Entwicklungszwecken können Sie mit Flashstation einen HWASan-fähigen Build von AOSP auf ein Pixel-Gerät mit entsperrtem Bootloader flashen . Wählen Sie das _hwasan-Ziel aus, z. B. aosp_flame_hwasan-userdebug. Weitere Einzelheiten finden Sie in der NDK-Dokumentation für HWAAn für App-Entwickler.

Bessere Stacktraces

HWASan verwendet einen schnellen, Frame-Pointer-basierten Unwinder, um einen Stack-Trace für jedes Speicherzuweisungs- und Freigabeereignis im Programm aufzuzeichnen. Android aktiviert standardmäßig Frame-Zeiger im AArch64-Code, sodass dies in der Praxis hervorragend funktioniert. Wenn Sie über verwalteten Code entspannen müssen, legen HWASAN_OPTIONS=fast_unwind_on_malloc=0 in der Prozessumgebung fest. Beachten Sie, dass Stack-Traces für fehlerhaften Speicherzugriff standardmäßig den „langsamen“ Unwinder verwenden; diese Einstellung betrifft nur Zuordnungs- und Freigabeablaufverfolgungen. Diese Option kann je nach Auslastung sehr CPU-intensiv sein.

Symbolisierung

Siehe Symbolisierung in „HWASan-Berichte verstehen“.

HWAAn in Apps

Ähnlich wie AddressSanitizer kann HWASan nicht in Java-Code sehen, aber es kann Fehler in den JNI-Bibliotheken erkennen. Im Gegensatz zu ASan wird das Ausführen von HWAAn-Apps auf einem Nicht-HWASan-Gerät nicht unterstützt.

Auf einem HWASan-Gerät können Apps mit HWASan überprüft werden, indem ihr Code mit SANITIZE_TARGET:=hwaddress in Make oder -fsanitize=hwaddress in Compiler-Flags erstellt wird. Weitere Einzelheiten finden Sie in der Dokumentation für App-Entwickler .