Puntata 8: di Vlad Tsyrklevich a Seattle, WA (novembre 2019)
Puntate precedenti
Il debug degli errori di sicurezza della memoria, come use-after-frees o overflow del buffer, può essere difficile. Strumenti come AddressSanitizer (ASan) sono utili per individuare gli errori di memoria nei test delle unità e nei fuzzer, ma molti bug si manifestano solo dopo il deployment agli utenti dove l'overhead di ASan è proibitivamente elevato.
GWP-ASan è un rilevatore di errori di memoria solo heap progettato per essere utilizzato in natura. Rileva use-after-free, overflow/underflow del buffer e doppio free. A differenza di ASan, non rileva errori nello stack o nei globali.
Campionando una piccola percentuale di allocazioni, GWP-ASan è in grado di fornire il rilevamento di errori probabilistici con un overhead di memoria e prestazioni trascurabile. GWP-ASan causerà l'arresto anomalo del processo immediatamente quando si verifica un errore di memoria con un'allocazione campionata. In questo modo è più facile individuare il bug perché l'arresto anomalo si verifica proprio dove viene commesso l'errore, invece che in un momento successivo quando viene utilizzata la memoria danneggiata.
Come ASan, i report sugli arresti anomali di GWP-ASan includono le analisi dello stack di allocazione e di deallocation per facilitare il debug dei problemi di memoria. Diamo un'occhiata a un esempio (crbug/956230) di alcuni dei dati aggiuntivi presentati nella UI degli arresti anomali:
L'utilizzo e la deallocation hanno entrambi origine in PDFiumEngine::ExtendSelection()
.
L'origine mostra rapidamente che il bug è l'uso di un iteratore std::vector
invalidato.
GWP-ASan è abilitato sul canale stabile per le allocazioni effettuate utilizzando malloc
/new
e PartitionAlloc
su Windows e macOS. È in corso il supporto di Android. Finora sono stati segnalati oltre 60 bug GWP-ASan e circa il 70% è stato risolto. Gli arresti anomali di GWP-ASan sono tutti problemi di sicurezza dei candidati che potrebbero essere sfruttabili, quindi valutali rapidamente e richiedi backport dove necessario.