AddressSanitizer con supporto hardware

Consulta Informazioni sui report HWASan per informazioni su come leggere gli arresti anomali di HWASan.

AddressSanitizer (HWASan) con l'aiuto dell'hardware è uno strumento di rilevamento degli errori di memoria simile a AddressSanitizer. HWASan utilizza molta meno RAM rispetto ad ASan, il che lo rende adatto per la pulizia dell'intero sistema. HWASan è disponibile solo su Android 10 e versioni successive e solo su hardware AArch64.

Sebbene sia utile principalmente per il codice C/C++, HWASan può anche contribuire a eseguire il debug del codice Java che causa arresti anomali in C/C++ utilizzati per implementare le interfacce Java. È utile perché rileva gli errori di memoria quando si verificano, indirizzandoti direttamente al codice responsabile.

Puoi eseguire il flashing di immagini HWASan precompilate sui dispositivi Pixel supportati da ci.android.com (istruzioni di configurazione dettagliate).

Rispetto all'ASAn classico, HWASan offre:

  • Overhead CPU simile (~2x)
  • Overhead simile per le dimensioni del codice (40-50%)
  • Overhead della RAM molto inferiore (10-35%)

HWASan rileva lo stesso insieme di bug di ASan:

  • Overflow/underflow del buffer dello stack e dell'heap
  • Utilizzo dell'heap dopo il rilascio
  • Utilizzo dell'elenco di controllo al di fuori dell'ambito
  • Doppio/libero/selvaggio

Inoltre, HWASan rileva l'utilizzo dello stack dopo il ritorno.

HWASan (come ASan) è compatibile con UBSan ed è possibile abilitare entrambi contemporaneamente su una destinazione.

Dettagli e limitazioni dell'implementazione

HWASan si basa sull'approccio di tagging della memoria, in cui un piccolo valore di tag casuale viene associato sia a puntatori sia a intervalli di indirizzi di memoria. Affinché l'accesso a una memoria sia valido, i tag di puntatore e di memoria devono corrispondere. HWASan si basa sulla funzionalità di ignoramento del byte superiore (TBI) di ARMv8, chiamata anche tagging degli indirizzi virtuali, per memorizzare il tag del puntatore nei bit più alti dell'indirizzo.

Scopri di più sulla progettazione di HWASan sul sito della documentazione di Clang.

Per impostazione predefinita, HWASan non dispone delle zone rosse di dimensioni limitate di ASan per il rilevamento degli overflow o della quarantena con capacità limitata di ASan per il rilevamento dell'utilizzo dopo la fine del periodo di prova. Per questo motivo, HWASan può rilevare un bug indipendentemente dalle dimensioni dell'overflow o dal tempo trascorso dall'allocazione della memoria. Questo offre a HWASan un grande vantaggio rispetto ad ASan.

Tuttavia, HWASan ha un numero limitato di possibili valori di tag (256), il che significa che esiste una probabilità dello 0,4% di perdere un bug durante un'esecuzione del programma.

Requisiti

Le versioni recenti (4.14 e successive) del kernel Android comune supportano HWASan out-of-the-box. I branch specifici di Android 10 non supportano HWASan.

Il supporto dello spazio utente per HWASan è disponibile a partire da Android 11.

Se stai lavorando con un kernel diverso, HWASan richiede che il kernel Linux accetti i cursori con tag negli argomenti delle chiamate di sistema. Il supporto è stato implementato nei seguenti patchset upstream:

Se esegui la compilazione con una toolchain personalizzata, assicurati che includa tutto fino al commit LLVM c336557f.

Utilizzare HWASan

Utilizza i seguenti comandi per creare l'intera piattaforma utilizzando HWASan:

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

Per comodità, puoi aggiungere l'impostazione SANITIZE_TARGET a una definizione di prodotto, in modo simile a aosp_coral_hwasan.

Per gli utenti che hanno dimestichezza con AddressSanitizer, è stata eliminata molta complessità di compilazione:

  • Non è necessario eseguire make due volte.
  • Le build incrementali sono pronte all'uso.
  • Non è necessario eseguire il flashing dei dati utente.

Sono state rimosse anche alcune limitazioni di AddressSanitizer:

  • Gli eseguibili statici sono supportati.
  • È consentito saltare la sanitizzazione di qualsiasi target diverso da libc. A differenza di ASan, non è necessario che se una libreria viene sottoposta a sanitizzazione, lo stesso debba essere fatto per qualsiasi file eseguibile che la collega.

Puoi passare liberamente da immagini HWASan a immagini normali con lo stesso numero di build (o superiore). Non è necessario resettare il dispositivo.

Per saltare la sanificazione di un modulo, usa LOCAL_NOSANITIZE := hwaddress (Android.mk) o sanitize: { hwaddress: false } (Android.bp).

Pulisci i singoli target

HWASan può essere attivato per target in una build normale (non sanificata), a condizione che anche libc.so sia sanificato. Aggiungi hwaddress: true al blocco di sanitizzazione in "libc_defaults" in bionic/libc/Android.bp. Ripeti la stessa operazione nel target su cui stai lavorando.

Tieni presente che la sanitizzazione di libc consente il tagging delle allocazioni di memoria heap a livello di sistema, nonché il controllo dei tag per le operazioni di memoria all'interno di libc.so. In questo modo è possibile rilevare bug anche nei binari per i quali HWASan non è stato attivato se l'accesso alla memoria errato si trova in libc.so (ad es. pthread_mutex_unlock() in un mutex di delete()ed).

Non è necessario modificare i file di compilazione se l'intera piattaforma viene compilata utilizzando HWASan.

Stazione flash

A scopo di sviluppo, puoi eseguire il flashing di una build di AOSP abilitata per HWASan su un dispositivo Pixel con bootloader sbloccato utilizzando Flashstation. Seleziona il target _hwasan, ad esempio aosp_flame_hwasan-userdebug. Per ulteriori dettagli, consulta la documentazione NDK per HWASan per gli sviluppatori di app.

Analisi dello stack migliori

HWASan utilizza un smontatore rapido basato su puntatori frame per registrare una traccia dello stack per ogni evento di allocazione e deallocazione della memoria nel programma. Android attiva i puntatori frame nel codice AArch64 per impostazione predefinita, quindi funziona perfettamente nella pratica. Se devi annullare il codice gestito, imposta HWASAN_OPTIONS=fast_unwind_on_malloc=0 nell'ambiente di processo. Tieni presente che le analisi dello stack di accesso alla memoria non valide utilizzano per impostazione predefinita il unwinder "lenta"; questa impostazione influisce solo sulle analisi di allocazione e deallocation. Questa opzione può richiedere molto tempo della CPU, a seconda del carico.

Simbolizzazione

Consulta la sezione Simbolizzazione in "Informazioni sui report HWASan".

HWASan nelle app

Come AddressSanitizer, HWASan non può esaminare il codice Java, ma può rilevare bug nelle librerie JNI. Fino ad Android 14, l'esecuzione di app HWASan su un dispositivo non HWASan non era supportata.

Su un dispositivo HWASan, è possibile controllare le app con HWASan creando il relativo codice con SANITIZE_TARGET:=hwaddress in Make o -fsanitize=hwaddress nei flag del compilatore. Su un dispositivo non HWASan (con Android 14 o versioni successive), è necessario aggiungere un'impostazione del file wrap.sh LD_HWASAN=1. Per ulteriori dettagli, consulta la documentazione per gli sviluppatori di app.