Saat alat HWASan mendeteksi bug memori, proses akan dihentikan dengan abort()
, dan
laporan dicetak ke {i>
stderr<i} dan {i>logcat<i}. Seperti semua masalah pada native code di Android, error HWASan dapat
ditemukan di bawah /data/tombstones
.
Dibandingkan dengan masalah pada native code reguler, HWASan membawa informasi tambahan di kolom “Batalkan pesan” di dekat bagian atas batu nisan. Lihat contoh error berbasis heap di bawah ini (untuk bug stack, lihat catatan di bawah untuk bagian khusus stack).
Contoh laporan
*** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** Build fingerprint: 'google/flame_hwasan/flame:Tiramisu/MASTER/7956676:userdebug/dev-keys' Revision: 'DVT1.0' ABI: 'arm64' Timestamp: 2019-04-24 01:13:22+0000 pid: 11154, tid: 11154, name: sensors@1.0-ser >>> /vendor/bin/hw/android.hardware.sensors@1.0-service <<< signal 6 (SIGABRT), code -1 (SI_QUEUE), fault addr -------- Abort message: '==9569==ERROR: HWAddressSanitizer: tag-mismatch on address 0x00433ae20045 at pc 0x00623ae2a9cc READ of size 1 at 0x00433ae20045 tags: 5b/83 (ptr/mem) in thread T0 #0 0x7240450c68 (/system/lib64/vndk-sp-R/libcutils.so+0x8c68) #1 0x723dffd490 (/vendor/lib64/sensors.ssc.so+0x34490) #2 0x723e0126e0 (/vendor/lib64/sensors.ssc.so+0x496e0) [...] [0x00433ae20040,0x00433ae20060) is a small unallocated heap chunk; size: 32 offset: 5 Cause: use-after-free 0x00433ae20045 is located 5 bytes inside of 10-byte region [0x00433ae20040,0x00433ae2004a) freed by thread T0 here: #0 0x72404d1b18 (/system/lib64/libclang_rt.hwasan-aarch64-android.so+0x10b18) #1 0x723af23040 (/vendor/lib64/libgralloccore.so+0x5040) #2 0x723af23fa4 (/vendor/lib64/libgralloccore.so+0x5fa4) [...] previously allocated here: #0 0x72404ce554 (/system/lib64/libclang_rt.hwasan-aarch64-android.so+0xd554) #1 0x7240115654 (/apex/com.android.runtime/lib64/bionic/libc.so+0x43654) #2 0x7240450ac8 (/system/lib64/vndk-sp-R/libcutils.so+0x8ac8) [...] hwasan_dev_note_heap_rb_distance: 1 1023 hwasan_dev_note_num_matching_addrs: 0 hwasan_dev_note_num_matching_addrs_4b: 0 Thread: T0 0x006a00002000 stack: [0x007fc1064000,0x007fc1864000) sz: 8388608 tls: [0x00737702ffc0,0x007377033000) Memory tags around the buggy address (one tag corresponds to 16 bytes): 0x006f33ae1f80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae1f90: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae1fa0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae1fb0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae1fc0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae1fd0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae1fe0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae1ff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 =>0x006f33ae2000: 08 00 08 00 [83] 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2010: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2020: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2030: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2040: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2050: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2060: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2070: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0x006f33ae2080: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 Tags for short granules around the buggy address (one tag corresponds to 16 bytes): 0x006f33ae1ff0: .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. =>0x006f33ae2000: 72 .. d0 .. [..] .. .. .. .. .. .. .. .. .. .. .. 0x006f33ae2010: .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. See https://clang.llvm.org/docs/HardwareAssistedAddressSanitizerDesign.html#short-granules for a description of short granule tags Registers where the failure occurred (pc 0x00623ae2a9cc): x0 0000007fc18623ec x1 5b0000433ae20045 x2 0000000000000013 x3 ffffffffffffffff x4 ffffffffffffffff x5 0000007fc1861da3 x6 6f7420676e696f47 x7 45522061206f6420 x8 0000000000000000 x9 0200006b00000000 x10 00000007fc18623f x11 5b0000433ae20040 x12 6f64206f7420676e x13 0a44414552206120 x14 0000000000000010 x15 ffffffffffffffff x16 000000737169ac94 x17 0000000000000007 x18 0000007377bd8000 x19 0000007fc1862498 x20 0200006b00000000 x21 0000007fc18624a8 x22 0000000000000001 x23 0000000000000000 x24 0000000000000000 x25 0000000000000000 x26 0000000000000000 x27 0000000000000000 x28 0000000000000000 x29 0000007fc1862410 x30 000000623ae2a9d0 sp 0000007fc18623d0 SUMMARY: HWAddressSanitizer: tag-mismatch (/system/lib64/vndk-sp-R/libcutils.so+0x8c68) [ … regular crash dump follows …]
Hal ini sangat mirip dengan laporan AddressSanitizer. Tidak seperti itu, hampir semua bug HWASan memiliki "tag-mismatch", yaitu akses memori di mana tag pointer melakukan tidak cocok dengan tag memori yang sesuai. Ini bisa menjadi salah satu
- melampaui batas akses pada stack atau heap
- gunakan setelah kosong di heap
- gunakan setelah return on stack
Bagian
Penjelasan dari setiap bagian laporan HWASan adalah sebagai berikut:
Error akses
Berisi informasi tentang akses memori yang buruk, termasuk:
- Jenis Akses ("BACA" vs. "TULIS")
- Ukuran akses (berapa byte yang dicoba untuk diakses)
- Nomor thread akses
- Tag pointer dan memori (untuk proses debug lanjutan)
Mengakses stack trace
Stack trace akses memori buruk. Lihat bagian Simbolisasi untuk melambangkan sesuatu.
Penyebab
Kemungkinan penyebab akses yang buruk. Jika ada beberapa kandidat, adalah terdaftar dengan urutan kemungkinan menurun. Mendahului info detail tentang penyebabnya. HWASan dapat mendiagnosis penyebab berikut:
- use-after-free
- stack tag-mismatch: dapat berupa stack use-after-return / use after-scope, atau di luar batas
- heap-buffer-overflow
- global-overflow
Informasi memori
Menjelaskan apa yang diketahui HWASan tentang memori yang sedang diakses, dan mungkin berbeda berdasarkan jenis {i>bug<i}.
Jenis Serangga | Penyebab | Format Laporan |
---|---|---|
tag tidak cocok | use-after-free |
<address> is located N bytes inside of M-byte region [<start>, <end>) freed by thread T0 here: |
heap-buffer-overflow | Perhatikan bahwa ini juga dapat berupa underflow.
<address> is located N bytes to the right of M-byte region [<start>, <end>) allocated here: |
|
ketidakcocokan tag stack | Laporan stack tidak membedakan antara {i>overflow/underflow<i} dan {i>use-after-return bug<i}. Di beberapa juga, untuk menemukan alokasi tumpukan yang merupakan sumber kesalahan, offline simbolisasi diperlukan. Lihat Memahami laporan stack di bawah ini. | |
tidak valid | use-after-free | Ini adalah bug gratis ganda. Jika ini terjadi saat penonaktifan proses, ini dapat menandakan bahwa
Pelanggaran ODR.
<address> is located N bytes inside of M-byte region [<start>, <end>) freed by thread T0 here: |
tidak dapat mendeskripsikan alamat | Dapat berupa {i>wildcard<i} (bebas dari memori yang belum pernah dialokasikan sebelumnya), atau bebas ganda setelah memori yang dialokasikan dikeluarkan dari {i>buffer <i}bebas HWASan. | |
0x... adalah memori bayangan HWAsan. | Ini benar-benar gratis, karena aplikasi mencoba untuk memori yang internal ke HWASan. |
Stack trace dealokasi
Stack trace tempat memori dibatalkan alokasinya. Hanya hadir untuk digunakan setelah gratis atau tidak ada bug yang tidak valid. Lihat bagian Simbolisasi untuk melambangkan.
Stack trace alokasi
Stack trace tempat memori dialokasikan. Lihat bagian Simbolisasi untuk melambangkan.
Proses debug lanjutan Informasi
Laporan HWASan juga menampilkan beberapa informasi proses debug lanjutan, termasuk (berurutan):
- Daftar thread dalam proses
- Daftar thread dalam proses
- Nilai tag memori di dekat memori faulting
- Dump register pada titik akses memori
Timbunan tag memori
Dump memori tag dapat digunakan untuk mencari alokasi memori di sekitar dengan tag yang sama sebagai kursor . Izin ini dapat menunjukkan akses di luar batas dengan offset besar. Satu tag sesuai dengan 16 byte memori; tag pointer adalah 8 bit teratas dari alamat tersebut. Dump memori tag dapat memberikan petunjuk, untuk contoh berikut ini adalah luapan buffer di sebelah kanan:
tags: ad/5c (ptr/mem) [...] Memory tags around the buggy address (one tag corresponds to 16 bytes): 0x006f33ae1ff0: 0e 0e 0e 57 20 20 20 20 20 2e 5e 5e 5e 5e 5e b5 =>0x006f33ae2000: f6 f6 f6 f6 f6 4c ad ad ad ad ad ad [5c] 5c 5c 5c 0x006f33ae2010: 5c 04 2e 2e 2e 2e 2e 2f 66 66 66 66 66 80 6a 6a Tags for short granules around the buggy address (one tag corresponds to 16 bytes): 0x006f33ae1ff0: ab 52 eb .. .. .. .. .. .. .. .. .. .. .. .. .. =>0x006f33ae2000: .. .. .. .. .. .. .. .. .. .. .. .. [..] .. .. .. 0x006f33ae2010: .. 5c .. .. .. .. .. .. .. .. .. .. .. .. .. ..(perhatikan run 6 × 16 = 96 byte tag "ad" di sebelah kiri yang cocok dengan tag pointer).
Jika ukuran alokasi bukan kelipatan 16, ukuran sisanya adalah disimpan sebagai tag memori dan tag tersebut akan disimpan sebagai tag granule. Pada contoh di atas, tepat setelah alokasi yang dicetak tebal diberi tag iklan, kami punya 5 × 16 + 4 = 84 byte alokasi tag 5c.
Tag memori nol (mis. tags: ad/00 (ptr/mem)
) biasanya menunjukkan
{i>stack-use-after-return bug<i}.
Daftarkan dump
Dump register dalam laporan HWASan sesuai dengan instruksi sebenarnya yang melakukan tidak valid memori akses. Ini diikuti oleh dump register lain dari pengendali sinyal Android reguler "-" abaikan yang kedua, diambil saat HWASan memanggil abort() dan tidak relevan dengan {i>bug<i} itu.
Simbolisasi
Untuk mendapatkan nama fungsi dan nomor baris dalam stack trace (dan mendapatkan nama variabel untuk use-after-scope) {i>bug<i}), diperlukan langkah simbolisasi offline.
Penyiapan pertama kali: instal llvm-symbolizer
Sebagai melambangkan, sistem Anda harus telah menginstal llvm-symbolizer dan dapat diakses dari $PATH. Di Debian, Anda dapat
menginstalnya menggunakan sudo apt install llvm
.
Mendapatkan file simbol
Untuk simbolisasi, kita membutuhkan biner unstripped yang berisi simbol. Tempat ditemukannya hal-hal tersebut bergantung pada jenis build:
Untuk build lokal, file simbol dapat ditemukan di
out/target/product/<product>/symbols/
.
Untuk build AOSP (mis., di-flash dari Flashstation),
build dapat ditemukan di Android CI. Di "Artefak" untuk
membangun,
akan ada file ${PRODUCT}-symbols-${BUILDID}.zip
.
Untuk build internal dari organisasi Anda, periksa dokumentasi organisasi untuk mendapatkan bantuan mendapatkan file simbol.
Simbolkan
hwasan_symbolize –-symbols <DECOMPRESSED_DIR>/out/target/product/*/symbols < crash
Memahami laporan stack
Untuk bug yang terjadi dengan variabel stack, laporan HWASan akan berisi detail seperti ini:
Cause: stack tag-mismatch Address 0x007d4d251e80 is located in stack of thread T64 Thread: T64 0x0074000b2000 stack: [0x007d4d14c000,0x007d4d255cb0) sz: 1088688 tls: [0x007d4d255fc0,0x007d4d259000) Previously allocated frames: record_addr:0x7df7300c98 record:0x51ef007df3f70fb0 (/apex/com.android.art/lib64/libart.so+0x570fb0) record_addr:0x7df7300c90 record:0x5200007df3cdab74 (/apex/com.android.art/lib64/libart.so+0x2dab74) [...]
Agar bug tumpukan dapat dipahami, HWASan melacak frame stack yang terjadi di masa lalu. Saat ini, HWASan tidak mengubahnya menjadi konten yang dapat dipahami manusia dalam laporan bug, dan memerlukan langkah simbolisasi tambahan.
Pelanggaran ODR
Beberapa bug setelah gratis yang dilaporkan oleh HWASan juga dapat menunjukkan pelanggaran One Definition Rule (ODR). Pelanggaran ODR terjadi jika variabel yang sama ditentukan beberapa kali dalam program yang sama. Ini juga berarti bahwa variabel itu dihancurkan beberapa kali, yang dapat menyebabkan {i>use-after-free<i}.
Setelah simbolisasi, pelanggaran ODR menunjukkan penggunaan setelah gratis dengan __cxa_finalize
,
pada stack akses yang tidak valid dan "dibebaskan di sini" {i>stack<i}. Kolom "yang dialokasikan sebelumnya
di sini" stack berisi __dl__ZN6soinfo17call_constructorsEv
dan seharusnya
menunjuk ke lokasi dalam program Anda yang mendefinisikan variabel yang lebih tinggi dalam tumpukan.
Salah satu alasan mengapa ODR dapat dilanggar adalah ketika library statis digunakan. Jika sebuah pustaka statis yang mendefinisikan C++ global ditautkan ke dalam beberapa pustaka bersama atau {i>executable<i}, beberapa definisi dari simbol yang sama mungkin berakhir ada di alamat yang sama yang akan menyebabkan kesalahan ODR.
Pemecahan masalah
HWAddressSanitizer tidak dapat mendeskripsikan alamat secara lebih detail
Terkadang HWASan dapat kehabisan ruang untuk informasi tentang alokasi memori sebelumnya. Dalam kasus tersebut, laporan hanya akan berisi satu stack trace untuk akses memori langsung, diikuti dengan sebuah catatan:
HWAddressSanitizer can not describe address in more detail.
Dalam beberapa kasus, hal ini dapat diatasi dengan menjalankan pengujian beberapa kali. Pilihan lain adalah meningkatkan HWASan
ukuran dokumen. Hal ini dapat dilakukan secara global di
build/soong/cc/sanitize.go
(cari
hwasanGlobalOptions
), atau dalam lingkungan proses Anda (coba
adb shell echo $HWASAN_OPTIONS
untuk melihat setelan saat ini).
Ini juga bisa terjadi jika memori yang diakses tidak dipetakan, atau dialokasikan oleh perangkat non-HWASan
alokator. Dalam hal ini, tag mem
yang tercantum di header error umumnya akan
00
. Jika Anda memiliki akses ke batu nisan yang lengkap, sebaiknya lihat
{i>memory dump<i} untuk mengetahui pemetaan
mana (jika ada) alamat tersebut.
Bug bertingkat di thread yang sama
Ini berarti ada bug saat membuat laporan error HWASan. Hal ini biasanya disebabkan oleh adanya {i>bug <i}di HWASan, harap laporkan bug dan memberikan petunjuk cara merekonstruksi masalah jika memungkinkan.