南京h5 網(wǎng)站建設(shè)展示型網(wǎng)站設(shè)計(jì)公司
前言
想必大家曾經(jīng)被各種Native Crash折磨過,本地測試沒啥問題,一到線上或者自動(dòng)化測試就出現(xiàn)各種SIGSEGV、SIGABRT、SIGILL、SIGBUS、SIGFPE異常,而且堆棧還是崩潰到libc.so這種,看起來跟我們的代碼沒啥關(guān)系,關(guān)鍵還不好復(fù)現(xiàn),簡直毫無辦法,做Android開發(fā)真的是太難了。
看看這個(gè)日志,是不是似曾相識(shí)?
--------- beginning of crash06-07 01:53:32.465 12027 12027 F DEBUG : *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***06-07 01:53:32.465 12027 12027 F DEBUG : Revision: '0'06-07 01:53:32.466 12027 12027 F DEBUG : ABI: 'arm64'06-07 01:53:32.466 12027 12027 F DEBUG : Timestamp: 2022-06-07 01:53:32.033409857+080006-07 01:53:32.466 12027 12027 F DEBUG : Process uptime: 0s06-07 01:53:32.466 12027 12027 F DEBUG : Cmdline: mediaserver6406-07 01:53:32.466 12027 12027 F DEBUG : pid: 1139, tid: 11981, name: NPDecoder >>> mediaserver64 <<<06-07 01:53:32.466 12027 12027 F DEBUG : uid: 101306-07 01:53:32.466 12027 12027 F DEBUG : tagged_addr_ctrl: 000000000000000106-07 01:53:32.466 12027 12027 F DEBUG : signal 11 (SIGSEGV), code 2 (SEGV_ACCERR), fault addr 0x7c02d886f006-07 01:53:32.466 12027 12027 F DEBUG : x0 79748c5e568e2ddc x1 0000007ca13c3618 x2 0000000000000000 x3 0000007ca129100006-07 01:53:32.466 12027 12027 F DEBUG : x4 0000000001909705 x5 0000000000000000 x6 0000007c02d88808 x7 b60625655bf0252f06-07 01:53:32.467 12027 12027 F DEBUG : x8 0000000000000080 x9 0000007ca126fed7 x10 0000000000000006 x11 0000007bfd0a81fc06-07 01:53:32.467 12027 12027 F DEBUG : x12 9ef8a95ca9649dbe x13 e44782d5ac38720e x14 0000007bfd0a8030 x15 0000001e56307b5c06-07 01:53:32.467 12027 12027 F DEBUG : x16 0000007c95dfdb70 x17 0000007c9844f118 x18 0000007bfaa28000 x19 b400007c13c246d006-07 01:53:32.467 12027 12027 F DEBUG : x20 0000007c02d88730 x21 b400007c13c67c00 x22 0000000000000415 x23 0000007c02d8900006-07 01:53:32.467 12027 12027 F DEBUG : x24 0000000000000002 x25 b400007c13c246d0 x26 b400007c13c67c00 x27 0000007c02d8900006-07 01:53:32.467 12027 12027 F DEBUG : x28 0000007ca13c2c28 x29 0000007c02d886f006-07 01:53:32.467 12027 12027 F DEBUG : lr 0000007c02d886f0 sp 0000007c02d886d0 pc 0000007c02d886f0 pst 000000008000100006-07 01:53:32.467 12027 12027 F DEBUG : backtrace:06-07 01:53:32.467 12027 12027 F DEBUG : #00 pc 00000000000f86f0 [anon:stack_and_tls:11981]
再看看這個(gè)表格,有沒有你的老朋友?
SIGSEGV | SEGV_MAPERR | 地址不在 /proc/self/maps 映射中 |
SEGV_ACCERR | 沒有訪問權(quán)限 | |
SEGV_MTESERR | MTE特有類型 | |
SIGABRT | 程序主動(dòng)退出,常見調(diào)用函數(shù)abort(),raise()等 | |
SIGILL | ILL_ILLOPC | 非法操作碼(opcode) |
ILL_ILLOPN | 非法操作數(shù)(operand) | |
ILL_ILLADR | 非法尋址 | |
ILL_ILLTRP | 非法trap,如_builtintrap()主動(dòng)崩潰 | |
ILL_PRVOPC | 非法特權(quán)操作碼(privileged opcode) | |
ILL_PRVREG | 非法特權(quán)寄存器(privileged register) | |
ILL_COPROC | 協(xié)處理器錯(cuò)誤 | |
ILL_BADSTK | 內(nèi)部堆棧錯(cuò)誤 | |
SIGBUS | BUS_ADRALN | 訪問地址未對齊 |
BUS_ADRERR | 訪問不存在的物理地址 | |
BUS_OBJERR | 特定對象的硬件錯(cuò)誤 | |
SIGFPE | FPE_INTDIV | 整數(shù)除以0 |
FPE_INTOVF | 整數(shù)溢出 | |
FPE_FLTDIV | 浮點(diǎn)數(shù)除以0 | |
FPE_FLTOVF | 浮點(diǎn)數(shù)上溢(overflow) | |
FPE_FLTUND | 浮點(diǎn)數(shù)下溢(underflow) | |
FPE_FLTRES | 浮點(diǎn)數(shù)結(jié)果不精確 | |
FPE_FLTINV | 無效的浮點(diǎn)運(yùn)算 | |
FPE_FLTSUB | 越界 |
上日志和表格來自陳冠有(小米)大佬的Android開發(fā)太難了,Native Crash的一切!
感興趣也可以看下英文文檔:Signal Codes
所以,這些崩潰到底能不能解決?95% 以上的崩潰都能解決或者規(guī)避,大部分的系統(tǒng)崩潰也是如此(來自張紹文的Android開發(fā)高手課:02 | 崩潰優(yōu)化(下):應(yīng)用崩潰了,你應(yīng)該如何去分析?)。當(dāng)然這話不能隨便說,主要看個(gè)人能力和團(tuán)隊(duì)技術(shù)積累。筆者作為一個(gè)Android Boy,更多的時(shí)候面對這些疑難雜癥的崩潰問題會(huì)感覺非常的無力,畢竟Native涉及到C、C++、Linux操作系統(tǒng)了,已經(jīng)不是同一個(gè)領(lǐng)域的問題。但筆者仍然期望能在瓶頸中尋找突破,我們可以被打敗但不可以被打倒,對吧。卷起來,生死看淡,不服就干。
嘗試復(fù)現(xiàn)內(nèi)存錯(cuò)誤
遇到找不到規(guī)律的問題或者無法復(fù)現(xiàn)的問題,有時(shí)候我們會(huì)想,要是能復(fù)現(xiàn)就好了。所以,如果我們知道什么樣的代碼會(huì)有什么樣的問題,那對于排查問題的思路會(huì)起到一定的幫助。
#include <jni.h>
#include <string>
#include <android/log.h>
extern "C" JNIEXPORT jstring JNICALL
Java_com_nxg_asantest_ASanTestUtil_stringFromJNI(JNIEnv* env,jclass clazz) {std::string hello = "Hello from C++";return env->NewStringUTF(hello.c_str());
}/*** 測試釋放后使用*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testUseAfterFree(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *array = new int[100];delete [] array;int i = array[0]; // BOOM__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}/*** 測試數(shù)組越界*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testHeapBufferOverflow(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *array = new int[100];array[101] = 0; // BOOMdelete [] array;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}/*** 測試棧溢出*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testStackBufferOverflow(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int stack_array[100];stack_array[100] = 0;
// return stack_array[argc + 100]; // BOOM__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}/*** 測試全局棧溢出*/
int global_array[100] = {-1};
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testGlobalBufferOverflow(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );global_array[101] = 0;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}int *ptr;
__attribute__((noinline))
void FunctionThatEscapesLocalObject() {int local[100];ptr = &local[0];
}
/*** 測試返回后使用*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testUseAfterReturn(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );FunctionThatEscapesLocalObject();ptr[0] = 1;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}/*** 測試超出作用域使用*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testUseAfterScope(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *p;{int x = 0;p = &x;}*p = 5;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}/*** 測試重復(fù)釋放*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testRepeatFree(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *p = new int[3];delete []p;delete []p;delete []p;delete []p;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}/*** 測試內(nèi)存泄露*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testMemoryLeak(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );void *p;p = new int[7];p = 0; // The memory is leaked here__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}
以上代碼來自sztaohongtao的深入淺出Android NDK之ASan檢測內(nèi)存越界
經(jīng)過測試發(fā)現(xiàn)
Java_com_nxg_asantest_ASanTestUtil_testStackBufferOverflow崩潰報(bào)錯(cuò):

Java_com_nxg_asantest_ASanTestUtil_testRepeatFree崩潰報(bào)錯(cuò):

其它方法均未報(bào)錯(cuò)。
什么是Address Sanitizer
從 API 級(jí)別 27 (Android O MR 1) 開始,Android NDK 可支持 Address Sanitizer(也稱為 ASan)。
ASan 是一種基于編譯器的快速檢測工具,用于檢測原生代碼中的內(nèi)存錯(cuò)誤。ASan 可以檢測以下問題:
堆棧和堆緩沖區(qū)上溢/下溢
釋放之后的堆使用情況
超出范圍的堆棧使用情況
重復(fù)釋放/錯(cuò)誤釋放
ASan 可在 32 位和 64 位 ARM 以及 x86 和 x86-64 上運(yùn)行。ASan 的 CPU 開銷約為 2 倍,代碼大小開銷在 50% 到 2 倍之間,并且內(nèi)存開銷很大(具體取決于您的分配模式,但約為 2 倍)。
對于 64 位 ARM,強(qiáng)烈建議使用 HWAddress Sanitizer。
更多介紹和集成步驟見官方文檔:Address Sanitizer,筆者就不啰嗦了。
Address Sanitizer檢測代碼錯(cuò)誤
按照官方文檔集成Address Sanitizer后我們看看這些有問題的代碼是否能被檢測到。
heap-use-after-free
/*** 測試釋放后使用*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testUseAfterFree(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *array = new int[100];delete [] array;int i = array[0]; // BOOM__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}
日志:
--------- beginning of main
02-19 17:54:11.970 2027 2027 D ASanCrash: enter fun Java_com_nxg_asantest_ASanTestUtil_testUseAfterFree ...
02-19 17:54:11.970 2007 2007 I wrap.sh : =================================================================
02-19 17:54:11.970 2007 2007 I wrap.sh : [1m[31m==2027==ERROR: AddressSanitizer: heap-use-after-free on address 0x004e793c08e0 at pc 0x00720d020018 bp 0x007feeeb7f10 sp 0x007feeeb7f08
02-19 17:54:11.970 2007 2007 I wrap.sh : [1m[0m[1m[34mREAD of size 4 at 0x004e793c08e0 thread T0 (om.nxg.asantest)[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : #0 0x720d020014 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x3014)
02-19 17:54:11.986 2007 2007 I wrap.sh : #1 0x7225622244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:54:11.986 2007 2007 I wrap.sh : #2 0x7225611608 (/apex/com.android.art/lib64/libart.so+0x211608)
02-19 17:54:11.986 2007 2007 I wrap.sh : #3 0x7225618964 (/apex/com.android.art/lib64/libart.so+0x218964)
02-19 17:54:11.986 2007 2007 I wrap.sh : #4 0x7225684208 (/apex/com.android.art/lib64/libart.so+0x284208)
02-19 17:54:11.986 2007 2007 I wrap.sh : #5 0x7225a1e8f8 (/apex/com.android.art/lib64/libart.so+0x61e8f8)
02-19 17:54:11.986 2007 2007 I wrap.sh : #6 0x722598fa68 (/apex/com.android.art/lib64/libart.so+0x58fa68)
02-19 17:54:11.986 2007 2007 I wrap.sh : #7 0x6fe01f74 (/apex/com.android.art/javalib/arm64/boot.oat+0xb2f74)
02-19 17:54:11.986 2007 2007 I wrap.sh :
02-19 17:54:11.986 2007 2007 I wrap.sh : [1m[32m0x004e793c08e0 is located 0 bytes inside of 400-byte region [0x004e793c08e0,0x004e793c0a70)
02-19 17:54:11.986 2007 2007 I wrap.sh : [1m[0m[1m[35mfreed by thread T0 (om.nxg.asantest) here:[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : #0 0x74c9999c64 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so+0xaac64)
02-19 17:54:11.986 2007 2007 I wrap.sh : #1 0x720d01ffb4 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x2fb4)
02-19 17:54:11.986 2007 2007 I wrap.sh : #2 0x7225622244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:54:11.986 2007 2007 I wrap.sh : #3 0x722594a874 (/apex/com.android.art/lib64/libart.so+0x54a874)
02-19 17:54:11.986 2007 2007 I wrap.sh :
02-19 17:54:11.986 2007 2007 I wrap.sh : [1m[35mpreviously allocated by thread T0 (om.nxg.asantest) here:[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : #0 0x74c999947c (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so+0xaa47c)
02-19 17:54:11.986 2007 2007 I wrap.sh : #1 0x720d01ff90 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x2f90)
02-19 17:54:11.986 2007 2007 I wrap.sh : #2 0x7225622244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:54:11.986 2007 2007 I wrap.sh : #3 0x722594a874 (/apex/com.android.art/lib64/libart.so+0x54a874)
02-19 17:54:11.986 2007 2007 I wrap.sh :
02-19 17:54:11.986 2007 2007 I wrap.sh : SUMMARY: AddressSanitizer: heap-use-after-free (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x3014)
02-19 17:54:11.986 2007 2007 I wrap.sh : Shadow bytes around the buggy address:
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf2780c0: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf2780d0: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf2780e0: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf2780f0: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf278100: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : =>0x0019cf278110: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m[[1m[35mfd[1m[0m][1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf278120: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf278130: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf278140: [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[35mfd[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf278150: [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : 0x0019cf278160: [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m [1m[31mfa[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Shadow byte legend (one shadow byte represents 8 application bytes):
02-19 17:54:11.986 2007 2007 I wrap.sh : Addressable: [1m[0m00[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Partially addressable: [1m[0m01[1m[0m [1m[0m02[1m[0m [1m[0m03[1m[0m [1m[0m04[1m[0m [1m[0m05[1m[0m [1m[0m06[1m[0m [1m[0m07[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Heap left redzone: [1m[31mfa[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Freed heap region: [1m[35mfd[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Stack left redzone: [1m[31mf1[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Stack mid redzone: [1m[31mf2[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Stack right redzone: [1m[31mf3[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Stack after return: [1m[35mf5[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Stack use after scope: [1m[35mf8[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Global redzone: [1m[31mf9[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Global init order: [1m[36mf6[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Poisoned by user: [1m[34mf7[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Container overflow: [1m[34mfc[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Array cookie: [1m[31mac[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Intra object redzone: [1m[33mbb[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : ASan internal: [1m[33mfe[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Left alloca redzone: [1m[34mca[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Right alloca redzone: [1m[34mcb[1m[0m
02-19 17:54:11.986 2007 2007 I wrap.sh : Shadow gap: [1m[0mcc[1m[0m
02-19 17:54:11.987 2007 2007 I wrap.sh : ==2027==ABORTING
--------- beginning of crash
02-19 17:54:11.987 2027 2027 F libc : Fatal signal 6 (SIGABRT), code -1 (SI_QUEUE) in tid 2027 (om.nxg.asantest), pid 2027 (om.nxg.asantest)
02-19 17:54:12.022 2137 2137 I crash_dump64: obtaining output fd from tombstoned, type: kDebuggerdTombstoneProto
02-19 17:54:12.022 762 762 I tombstoned: received crash request for pid 2027
02-19 17:54:12.023 2137 2137 I crash_dump64: performing dump of process 2027 (target tid = 2027)
02-19 17:54:12.029 2137 2137 E DEBUG : failed to read /proc/uptime: Permission denied
02-19 17:54:12.238 2137 2137 F DEBUG : *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***
02-19 17:54:12.238 2137 2137 F DEBUG : Build fingerprint: 'google/flame/flame:12/SQ1A.211205.008/7888514:user/release-keys'
02-19 17:54:12.238 2137 2137 F DEBUG : Revision: 'MP1.0'
02-19 17:54:12.238 2137 2137 F DEBUG : ABI: 'arm64'
02-19 17:54:12.238 2137 2137 F DEBUG : Timestamp: 2023-02-19 17:54:12.029573192+0800
02-19 17:54:12.238 2137 2137 F DEBUG : Process uptime: 0s
02-19 17:54:12.238 2137 2137 F DEBUG : Cmdline: com.nxg.asantest
02-19 17:54:12.238 2137 2137 F DEBUG : pid: 2027, tid: 2027, name: om.nxg.asantest >>> com.nxg.asantest <<<
02-19 17:54:12.238 2137 2137 F DEBUG : uid: 10229
02-19 17:54:12.238 2137 2137 F DEBUG : signal 6 (SIGABRT), code -1 (SI_QUEUE), fault addr --------
02-19 17:54:12.238 2137 2137 F DEBUG : Abort message: '=================================================================
02-19 17:54:12.238 2137 2137 F DEBUG : ==2027==ERROR: AddressSanitizer: heap-use-after-free on address 0x004e793c08e0 at pc 0x00720d020018 bp 0x007feeeb7f10 sp 0x007feeeb7f08
02-19 17:54:12.238 2137 2137 F DEBUG : READ of size 4 at 0x004e793c08e0 thread T0 (om.nxg.asantest)
02-19 17:54:12.238 2137 2137 F DEBUG : #0 0x720d020014 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x3014)
02-19 17:54:12.238 2137 2137 F DEBUG : #1 0x7225622244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:54:12.238 2137 2137 F DEBUG : #2 0x7225611608 (/apex/com.android.art/lib64/libart.so+0x211608)
02-19 17:54:12.238 2137 2137 F DEBUG : #3 0x7225618964 (/apex/com.android.art/lib64/libart.so+0x218964)
02-19 17:54:12.238 2137 2137 F DEBUG : #4 0x7225684208 (/apex/com.android.art/lib64/libart.so+0x284208)
02-19 17:54:12.238 2137 2137 F DEBUG : #5 0x7225a1e8f8 (/apex/com.android.art/lib64/libart.so+0x61e8f8)
02-19 17:54:12.238 2137 2137 F DEBUG : #6 0x722598fa68 (/apex/com.android.art/lib64/libart.so+0x58fa68)
02-19 17:54:12.238 2137 2137 F DEBUG : #7 0x6fe01f74 (/apex/com.android.art/javalib/arm64/boot.oat+0xb2f74)
02-19 17:54:12.238 2137 2137 F DEBUG :
02-19 17:54:12.238 2137 2137 F DEBUG : 0x004e793c08e0 is located 0 bytes inside of 400-byte region [0x004e793c08e0,0x004e793c0a70)
02-19 17:54:12.238 2137 2137 F DEBUG : freed by thread T0 (om.nxg.asantest) here:
02-19 17:54:12.238 2137 2137 F DEBUG : #0 0x74c9999c64 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so+0xaac64)
02-19 17:54:12.238 2137 2137 F DEBUG : #1 0x720d01ffb4 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x2fb4)
02-19 17:54:12.238 2137 2137 F DEBUG : #2 0x7225622244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:54:12.238 2137 2137 F DEBUG : #3 0x722594a874 (/apex/com.android.art/lib64/libart.so+0x54a874)
02-19 17:54:12.238 2137 2137 F DEBUG :
02-19 17:54:12.238 2137 2137 F DEBUG : previously allocated by thread T0 (om.nxg.asantest) here:
02-19 17:54:12.238 2137 2137 F DEBUG : #0 0x74c999947c (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so+0xaa47c)
02-19 17:54:12.238 2137 2137 F DEBUG : #1 0x720d01ff90 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x2f90)
02-19 17:54:12.238 2137 2137 F DEBUG : #2 0x7225622244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:54:12.238 2137 2137 F DEBUG : #3 0x722594a874 (/apex/com.android.art/lib64/libart.so+0x54a874)
02-19 17:54:12.238 2137 2137 F DEBUG :
02-19 17:54:12.238 2137 2137 F DEBUG : SUMMARY: AddressSanitizer: heap-use-after-free (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x3014)
02-19 17:54:12.238 2137 2137 F DEBUG : Shadow bytes around the buggy address:
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf2780c0: fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf2780d0: fd fd fd fd fd fd fa fa fa fa fa fa fa fa fa fa
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf2780e0: fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf2780f0: fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf278100: fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd
02-19 17:54:12.238 2137 2137 F DEBUG : =>0x0019cf278110: fd fd fa fa fa fa fa fa fa fa fa fa[fd]fd fd fd
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf278120: fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf278130: fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd fd
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf278140: fd fd fd fd fd fd fd fd fd fd fd fd fd fd fa fa
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf278150: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
02-19 17:54:12.238 2137 2137 F DEBUG : 0x0019cf278160: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
02-19 17:54:12.238 2137 2137 F DEBUG : Shadow byte legend (one shadow byte represents 8 application bytes):
02-19 17:54:12.238 2137 2137 F DEBUG : Addressable: 00
02-19 17:54:12.238 2137 2137 F DEBUG : Partially addressable: 01 02 03 04 05 06 07
02-19 17:54:12.238 2137 2137 F DEBUG : Heap left redzone: fa
02-19 17:54:12.238 2137 2137 F DEBUG : Freed heap region: fd
02-19 17:54:12.238 2137 2137 F DEBUG : Stack left redzone: f1
02-19 17:54:12.238 2137 2137 F DEBUG : Stack mid redzone: f2
02-19 17:54:12.238 2137 2137 F DEBUG : Stack right redzone: f3
02-19 17:54:12.238 2137 2137 F DEBUG : Stack after return: f5
02-19 17:54:12.238 2137 2137 F DEBUG : Stack use after scope: f8
02-19 17:54:12.238 2137 2137 F DEBUG : Global redzone: f9
02-19 17:54:12.238 2137 2137 F DEBUG : Global init order: f6
02-19 17:54:12.238 2137 2137 F DEBUG : Poisoned by user: f7
02-19 17:54:12.238 2137 2137 F DEBUG : Container overflow: fc
02-19 17:54:12.238 2137 2137 F DEBUG : Array cookie: ac
02-19 17:54:12.238 2137 2137 F DEBUG : Intra object redzone: bb
02-19 17:54:12.238 2137 2137 F DEBUG : ASan internal: fe
02-19 17:54:12.238 2137 2137 F DEBUG : Left alloca redzone: ca
02-19 17:54:12.238 2137 2137 F DEBUG : Right alloca redzone: cb
02-19 17:54:12.238 2137 2137 F DEBUG : Shadow gap: cc
02-19 17:54:12.238 2137 2137 F DEBUG : '
02-19 17:54:12.238 2137 2137 F DEBUG : x0 0000000000000000 x1 00000000000007eb x2 0000000000000006 x3 0000007feeeb7190
02-19 17:54:12.238 2137 2137 F DEBUG : x4 0000000000000000 x5 0000000000000000 x6 0000000000000000 x7 0000000000000000
02-19 17:54:12.238 2137 2137 F DEBUG : x8 00000000000000f0 x9 ea2bc60daeb39863 x10 0000000000000000 x11 ffffff80fffffbdf
02-19 17:54:12.238 2137 2137 F DEBUG : x12 0000000000000001 x13 0000000000000037 x14 0000000000000030 x15 00000074c9938d54
02-19 17:54:12.238 2137 2137 F DEBUG : x16 00000074df784050 x17 00000074df760eb0 x18 00000074e69d2000 x19 00000000000007eb
02-19 17:54:12.238 2137 2137 F DEBUG : x20 00000000000007eb x21 00000000ffffffff x22 00000074c9a77040 x23 00000074c9b00e00
02-19 17:54:12.238 2137 2137 F DEBUG : x24 000000720d020018 x25 0000000000000001 x26 0000000018380001 x27 00000057793e8100
02-19 17:54:12.238 2137 2137 F DEBUG : x28 0000007feeeb7f90 x29 0000007feeeb7210
02-19 17:54:12.238 2137 2137 F DEBUG : lr 00000074df713ba0 sp 0000007feeeb7170 pc 00000074df713bcc pst 0000000000000000
02-19 17:54:12.238 2137 2137 F DEBUG : backtrace:
02-19 17:54:12.238 2137 2137 F DEBUG : #00 pc 000000000004fbcc /apex/com.android.runtime/lib64/bionic/libc.so (abort+164) (BuildId: ba489d4985c0cf173209da67405662f9)
02-19 17:54:12.238 2137 2137 F DEBUG : #01 pc 000000000004d60c /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so (BuildId: 1faa253e88d6ebbf067a087f1b98301177b89a56)
02-19 17:54:12.238 2137 2137 F DEBUG : #02 pc 000000000004c5d8 /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so (BuildId: 1faa253e88d6ebbf067a087f1b98301177b89a56)
02-19 17:54:12.238 2137 2137 F DEBUG : #03 pc 00000000000a3300 /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so (BuildId: 1faa253e88d6ebbf067a087f1b98301177b89a56)
02-19 17:54:12.238 2137 2137 F DEBUG : #04 pc 00000000000a47dc /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so (BuildId: 1faa253e88d6ebbf067a087f1b98301177b89a56)
02-19 17:54:12.238 2137 2137 F DEBUG : #05 pc 00000000000a5084 /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so (__asan_report_load4+44) (BuildId: 1faa253e88d6ebbf067a087f1b98301177b89a56)
02-19 17:54:12.238 2137 2137 F DEBUG : #06 pc 0000000000003014 /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so (Java_com_nxg_asantest_ASanTestUtil_testUseAfterFree+216) (BuildId: b3fbe503c7eb01bc04ef889c04f547510728d2a0)
02-19 17:54:12.238 2137 2137 F DEBUG : #07 pc 0000000000222244 /apex/com.android.art/lib64/libart.so (art_quick_generic_jni_trampoline+148) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #08 pc 0000000000211608 /apex/com.android.art/lib64/libart.so (nterp_helper+152) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #09 pc 00000000000004cc [anon:dalvik-classes3.dex extracted in memory from /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/base.apk!classes3.dex] (com.nxg.asantest.MainActivity.onBtnUseAfterFreeClick+0)
02-19 17:54:12.238 2137 2137 F DEBUG : #10 pc 0000000000218964 /apex/com.android.art/lib64/libart.so (art_quick_invoke_stub+548) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #11 pc 0000000000284208 /apex/com.android.art/lib64/libart.so (art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char const*)+188) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #12 pc 000000000061e8f8 /apex/com.android.art/lib64/libart.so (_jobject* art::InvokeMethod<(art::PointerSize)8>(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, _jobject*, _jobject*, unsigned long)+1384) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #13 pc 000000000058fa68 /apex/com.android.art/lib64/libart.so (art::Method_invoke(_JNIEnv*, _jobject*, _jobject*, _jobjectArray*)+52) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #14 pc 00000000000b2f74 /apex/com.android.art/javalib/arm64/boot.oat (art_jni_trampoline+132) (BuildId: 715d0a044ea13bcf499cd6094001f85c3246944e)
02-19 17:54:12.238 2137 2137 F DEBUG : #15 pc 0000000000212520 /apex/com.android.art/lib64/libart.so (nterp_helper+4016) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #16 pc 00000000000bad4a [anon:dalvik-classes.dex extracted in memory from /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/base.apk] (androidx.appcompat.app.AppCompatViewInflater$DeclaredOnClickListener.onClick+46)
02-19 17:54:12.238 2137 2137 F DEBUG : #17 pc 0000000000706184 /system/framework/arm64/boot-framework.oat (android.view.View.performClick+148) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #18 pc 0000000000212520 /apex/com.android.art/lib64/libart.so (nterp_helper+4016) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #19 pc 000000000020c8ee [anon:dalvik-classes.dex extracted in memory from /data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/base.apk] (com.google.android.material.button.MaterialButton.performClick+6)
02-19 17:54:12.238 2137 2137 F DEBUG : #20 pc 0000000000640174 /system/framework/arm64/boot-framework.oat (android.view.View$PerformClick.run+164) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #21 pc 00000000004efe30 /system/framework/arm64/boot-framework.oat (android.os.Handler.dispatchMessage+80) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #22 pc 00000000004f2ccc /system/framework/arm64/boot-framework.oat (android.os.Looper.loopOnce+1036) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #23 pc 00000000004f2824 /system/framework/arm64/boot-framework.oat (android.os.Looper.loop+516) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #24 pc 00000000002cefdc /system/framework/arm64/boot-framework.oat (android.app.ActivityThread.main+732) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #25 pc 0000000000218be8 /apex/com.android.art/lib64/libart.so (art_quick_invoke_static_stub+568) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #26 pc 0000000000284224 /apex/com.android.art/lib64/libart.so (art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char const*)+216) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #27 pc 000000000061e8f8 /apex/com.android.art/lib64/libart.so (_jobject* art::InvokeMethod<(art::PointerSize)8>(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, _jobject*, _jobject*, unsigned long)+1384) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #28 pc 000000000058fa68 /apex/com.android.art/lib64/libart.so (art::Method_invoke(_JNIEnv*, _jobject*, _jobject*, _jobjectArray*)+52) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #29 pc 00000000000b2f74 /apex/com.android.art/javalib/arm64/boot.oat (art_jni_trampoline+132) (BuildId: 715d0a044ea13bcf499cd6094001f85c3246944e)
02-19 17:54:12.238 2137 2137 F DEBUG : #30 pc 000000000081a48c /system/framework/arm64/boot-framework.oat (com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run+140) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #31 pc 0000000000213344 /apex/com.android.art/lib64/libart.so (nterp_helper+7636) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #32 pc 000000000024b69e /system/framework/framework.jar (com.android.internal.os.WrapperInit.main+182)
02-19 17:54:12.238 2137 2137 F DEBUG : #33 pc 0000000000218be8 /apex/com.android.art/lib64/libart.so (art_quick_invoke_static_stub+568) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #34 pc 0000000000284224 /apex/com.android.art/lib64/libart.so (art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char const*)+216) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #35 pc 000000000061f050 /apex/com.android.art/lib64/libart.so (art::JValue art::InvokeWithVarArgs<art::ArtMethod*>(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, art::ArtMethod*, std::__va_list)+448) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #36 pc 000000000061f514 /apex/com.android.art/lib64/libart.so (art::JValue art::InvokeWithVarArgs<_jmethodID*>(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, _jmethodID*, std::__va_list)+92) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #37 pc 0000000000497b24 /apex/com.android.art/lib64/libart.so (art::JNI<false>::CallStaticVoidMethodV(_JNIEnv*, _jclass*, _jmethodID*, std::__va_list)+616) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #38 pc 00000000000aeac4 /system/lib64/libandroid_runtime.so (_JNIEnv::CallStaticVoidMethod(_jclass*, _jmethodID*, ...)+120) (BuildId: e6f683896552e00197598ae4519fb02d)
02-19 17:54:12.238 2137 2137 F DEBUG : #39 pc 00000000000b65d0 /system/lib64/libandroid_runtime.so (android::AndroidRuntime::callMain(android::String8 const&, _jclass*, android::Vector<android::String8> const&)+336) (BuildId: e6f683896552e00197598ae4519fb02d)
02-19 17:54:12.238 2137 2137 F DEBUG : #40 pc 0000000000002980 /system/bin/app_process64 (android::AppRuntime::onStarted()+68) (BuildId: 4ecb2c57d6667e4a94a73568ce392d22)
02-19 17:54:12.238 2137 2137 F DEBUG : #41 pc 000000000018cba8 /system/framework/arm64/boot-framework.oat (art_jni_trampoline+88) (BuildId: 129a000a0763e5ab511b5552db418f26d6b2c92f)
02-19 17:54:12.238 2137 2137 F DEBUG : #42 pc 0000000000211608 /apex/com.android.art/lib64/libart.so (nterp_helper+152) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #43 pc 00000000002484e0 /system/framework/framework.jar (com.android.internal.os.RuntimeInit.main+48)
02-19 17:54:12.238 2137 2137 F DEBUG : #44 pc 0000000000218be8 /apex/com.android.art/lib64/libart.so (art_quick_invoke_static_stub+568) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #45 pc 0000000000284224 /apex/com.android.art/lib64/libart.so (art::ArtMethod::Invoke(art::Thread*, unsigned int*, unsigned int, art::JValue*, char const*)+216) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #46 pc 000000000061f050 /apex/com.android.art/lib64/libart.so (art::JValue art::InvokeWithVarArgs<art::ArtMethod*>(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, art::ArtMethod*, std::__va_list)+448) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #47 pc 000000000061f514 /apex/com.android.art/lib64/libart.so (art::JValue art::InvokeWithVarArgs<_jmethodID*>(art::ScopedObjectAccessAlreadyRunnable const&, _jobject*, _jmethodID*, std::__va_list)+92) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #48 pc 0000000000497b24 /apex/com.android.art/lib64/libart.so (art::JNI<false>::CallStaticVoidMethodV(_JNIEnv*, _jclass*, _jmethodID*, std::__va_list)+616) (BuildId: e6c658201ef1ec3760112fa1b838ab2c)
02-19 17:54:12.238 2137 2137 F DEBUG : #49 pc 00000000000aeac4 /system/lib64/libandroid_runtime.so (_JNIEnv::CallStaticVoidMethod(_jclass*, _jmethodID*, ...)+120) (BuildId: e6f683896552e00197598ae4519fb02d)
02-19 17:54:12.238 2137 2137 F DEBUG : #50 pc 00000000000ba05c /system/lib64/libandroid_runtime.so (android::AndroidRuntime::start(char const*, android::Vector<android::String8> const&, bool)+836) (BuildId: e6f683896552e00197598ae4519fb02d)
02-19 17:54:12.238 2137 2137 F DEBUG : #51 pc 000000000000258c /system/bin/app_process64 (main+1336) (BuildId: 4ecb2c57d6667e4a94a73568ce392d22)
02-19 17:54:12.238 2137 2137 F DEBUG : #52 pc 00000000000488c8 /apex/com.android.runtime/lib64/bionic/libc.so (__libc_init+96) (BuildId: ba489d4985c0cf173209da67405662f9)
02-19 17:54:12.249 762 762 E tombstoned: Tombstone written to: tombstone_23
ASan檢測到了heap-use-after-free并主動(dòng)的拋出了異常。
[1m[31m==2027==ERROR: AddressSanitizer: heap-use-after-free on address 0x004e793c08e0 at pc 0x00720d020018 bp 0x007feeeb7f10 sp 0x007feeeb7f08
[1m[0m[1m[34mREAD of size 4 at 0x004e793c08e0 thread T0 (om.nxg.asantest)[1m[0m
#0 0x720d020014 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x3014)
但是我們并不知道具體報(bào)錯(cuò)是哪行代碼,日志只告訴了我們報(bào)錯(cuò)在libasantest.so的內(nèi)存地址0x3014,這時(shí)候addr2line就派上用場了。
addr2line全寫是address to line,ta是將函數(shù)地址解析成文件名或行號(hào)的工具。給出一個(gè)可執(zhí)行文件中的地址或一個(gè)可重定位對象中的偏移部分的地址,使用調(diào)試信息來找出與之相關(guān)的文件名和行號(hào)。
addr2line在NDK的這個(gè)路徑:

#注意NDK?23貌似已經(jīng)移除了arm-linux-androideabi-addr2line
~/Android/Sdk/ndk/21.4.7075529/toolchains/aarch64-linux-android-4.9/prebuilt/linux-x86_64/bin$
打開命令行終端,執(zhí)行:./arm-linux-androideabi-addr2line?-h查看使用幫助

Usage: ./aarch64-linux-android-addr2line [option(s)] [addr(s)]
Convert addresses into line number/file name pairs.
If no addresses are specified on the command line, they will be read from stdin
The options are:
@<file> Read options from <file>
-a --addresses Show addresses
-b --target=<bfdname> Set the binary file format
-e --exe=<executable> Set the input file name (default is a.out)
-i --inlines Unwind inlined functions
-j --section=<name> Read section-relative offsets instead of addresses
-p --pretty-print Make the output easier to read for humans
-s --basenames Strip directory names
-f --functions Show function names
-C --demangle[=style] Demangle function names
-h --help Display this information
-v --version Display the program's version
使用-e指定so文件,使用-a查詢內(nèi)存地址對應(yīng)的代碼行,執(zhí)行:
./aarch64-linux-android-addr2line -e /work/AndroidStudioProjects/AndroidDevelopmentPractices/ASanTest/app/src/main/cpp/obj/arm64-v8a/libasantest.so -a 0x3014
可以看到,打印了指定文件的代碼行數(shù):
/work/AndroidStudioProjects/AndroidDevelopmentPractices/ASanTest/app/src/main/cpp/native-lib.cpp:21

精準(zhǔn)的定位到了我們的代碼,確實(shí)很強(qiáng)大。
如果發(fā)現(xiàn)addr2line定位不到代碼行,比如返回?啥的,原因可能是so是release版本,建議使用debug版本測試,或者保留符號(hào)表。CMAKE開啟debug模式:
set(CMAKE_BUILD_TYPE DEBUG)?# 調(diào)試模式,方便addr2line定位代碼
heap-buffer-overflow
/*** 測試數(shù)組越界*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testHeapBufferOverflow(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *array = new int[100];array[101] = 0; // BOOMdelete [] array;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}
ASan檢測到了heap-buffer-overflow并主動(dòng)的拋出了異常。
02-19 17:57:24.109 3088 3088 I wrap.sh : [1m[31m==3095==ERROR: AddressSanitizer: heap-buffer-overflow on address 0x004e0ef77d14 at pc 0x0078b1f95118 bp 0x007fe23b0850 sp 0x007fe23b0848
02-19 17:57:24.109 3088 3088 I wrap.sh : [1m[0m[1m[34mWRITE of size 4 at 0x004e0ef77d14 thread T0 (om.nxg.asantest)[1m[0m
02-19 17:57:24.126 3088 3088 I wrap.sh : #0 0x78b1f95114 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x3114)
02-19 17:57:24.126 3088 3088 I wrap.sh : #1 0x792e222244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:57:24.126 3088 3088 I wrap.sh : #2 0x792e211608 (/apex/com.android.art/lib64/libart.so+0x211608)
02-19 17:57:24.126 3088 3088 I wrap.sh : #3 0x792e218964 (/apex/com.android.art/lib64/libart.so+0x218964)
02-19 17:57:24.127 3088 3088 I wrap.sh : #4 0x792e284208 (/apex/com.android.art/lib64/libart.so+0x284208)
02-19 17:57:24.127 3088 3088 I wrap.sh : #5 0x792e61e8f8 (/apex/com.android.art/lib64/libart.so+0x61e8f8)
02-19 17:57:24.127 3088 3088 I wrap.sh : #6 0x792e58fa68 (/apex/com.android.art/lib64/libart.so+0x58fa68)
02-19 17:57:24.127 3088 3088 I wrap.sh : #7 0x706d6f74 (/apex/com.android.art/javalib/arm64/boot.oat+0xb2f74)
addr2line定位到native-lib.cpp:31

對應(yīng)代碼如下:

stack-buffer-overflow
/*** 測試棧溢出*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testStackBufferOverflow(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int stack_array[100];stack_array[100] = 0;
// return stack_array[argc + 100]; // BOOM__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}
ASan檢測到了stack-buffer-overflow并主動(dòng)的拋出了異常。
02-19 17:57:27.190 3174 3174 I wrap.sh : =================================================================
02-19 17:57:27.191 3174 3174 I wrap.sh : [1m[31m==3185==ERROR: AddressSanitizer: stack-buffer-overflow on address 0x007fc42f3650 at pc 0x0079cf3ed340 bp 0x007fc42f3490 sp 0x007fc42f3488
02-19 17:57:27.191 3174 3174 I wrap.sh : [1m[0m[1m[34mWRITE of size 4 at 0x007fc42f3650 thread T0 (om.nxg.asantest)[1m[0m
02-19 17:57:27.206 3174 3174 I wrap.sh : #0 0x79cf3ed33c (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x333c)
02-19 17:57:27.207 3174 3174 I wrap.sh : #1 0x7a4ce22244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:57:27.207 3174 3174 I wrap.sh : #2 0x7a4ce11608 (/apex/com.android.art/lib64/libart.so+0x211608)
02-19 17:57:27.207 3174 3174 I wrap.sh : #3 0x7a4ce18964 (/apex/com.android.art/lib64/libart.so+0x218964)
02-19 17:57:27.207 3174 3174 I wrap.sh : #4 0x7a4ce84208 (/apex/com.android.art/lib64/libart.so+0x284208)
02-19 17:57:27.207 3174 3174 I wrap.sh : #5 0x7a4d21e8f8 (/apex/com.android.art/lib64/libart.so+0x61e8f8)
02-19 17:57:27.207 3174 3174 I wrap.sh : #6 0x7a4d18fa68 (/apex/com.android.art/lib64/libart.so+0x58fa68)
02-19 17:57:27.207 3174 3174 I wrap.sh : #7 0x6f547f74 (/apex/com.android.art/javalib/arm64/boot.oat+0xb2f74)
addr2line定位到native-lib.cpp:42

對應(yīng)代碼如下:

global-buffer-overflow
/*** 測試全局棧溢出*/
int global_array[100] = {-1};
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testGlobalBufferOverflow(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );global_array[101] = 0;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}
ASan檢測到了global-buffer-overflow并主動(dòng)的拋出了異常。
02-19 17:57:30.360 3282 3282 I wrap.sh : [1m[31m==3300==ERROR: AddressSanitizer: global-buffer-overflow on address 0x006d4bc22194 at pc 0x006d4bc184d0 bp 0x007ff88fe320 sp 0x007ff88fe318
02-19 17:57:30.360 3282 3282 I wrap.sh : [1m[0m[1m[34mWRITE of size 4 at 0x006d4bc22194 thread T0 (om.nxg.asantest)[1m[0m
02-19 17:57:30.378 3282 3282 I wrap.sh : #0 0x6d4bc184cc (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x34cc)
02-19 17:57:30.378 3282 3282 I wrap.sh : #1 0x6dcbc22244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:57:30.378 3282 3282 I wrap.sh : #2 0x6dcbc11608 (/apex/com.android.art/lib64/libart.so+0x211608)
02-19 17:57:30.378 3282 3282 I wrap.sh : #3 0x6dcbc18964 (/apex/com.android.art/lib64/libart.so+0x218964)
02-19 17:57:30.378 3282 3282 I wrap.sh : #4 0x6dcbc84208 (/apex/com.android.art/lib64/libart.so+0x284208)
02-19 17:57:30.378 3282 3282 I wrap.sh : #5 0x6dcc01e8f8 (/apex/com.android.art/lib64/libart.so+0x61e8f8)
02-19 17:57:30.378 3282 3282 I wrap.sh : #6 0x6dcbf8fa68 (/apex/com.android.art/lib64/libart.so+0x58fa68)
02-19 17:57:30.378 3282 3282 I wrap.sh : #7 0x6f9e0f74 (/apex/com.android.art/javalib/arm64/boot.oat+0xb2f74)
addr2line定位到native-lib.cpp:53

對應(yīng)代碼如下:

stack-use-after-scope
/*** 測試超出作用域使用*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testUseAfterScope(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *p;{int x = 0;p = &x;}*p = 5;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}
ASan檢測到了stack-use-after-scope并主動(dòng)的拋出了異常。
02-19 17:57:44.159 3512 3512 I wrap.sh : [1m[31m==3521==ERROR: AddressSanitizer: stack-use-after-scope on address 0x007feb36d4e0 at pc 0x00789a18d9bc bp 0x007feb36d4b0 sp 0x007feb36d4a8
02-19 17:57:44.159 3512 3512 I wrap.sh : [1m[0m[1m[34mWRITE of size 4 at 0x007feb36d4e0 thread T0 (om.nxg.asantest)[1m[0m
02-19 17:57:44.184 3512 3512 I wrap.sh : #0 0x789a18d9b8 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x39b8)
02-19 17:57:44.184 3512 3512 I wrap.sh : #1 0x7921a22244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:57:44.184 3512 3512 I wrap.sh : #2 0x7921a11608 (/apex/com.android.art/lib64/libart.so+0x211608)
02-19 17:57:44.184 3512 3512 I wrap.sh : #3 0x7921a18964 (/apex/com.android.art/lib64/libart.so+0x218964)
02-19 17:57:44.184 3512 3512 I wrap.sh : #4 0x7921a84208 (/apex/com.android.art/lib64/libart.so+0x284208)
02-19 17:57:44.184 3512 3512 I wrap.sh : #5 0x7921e1e8f8 (/apex/com.android.art/lib64/libart.so+0x61e8f8)
02-19 17:57:44.184 3512 3512 I wrap.sh : #6 0x7921d8fa68 (/apex/com.android.art/lib64/libart.so+0x58fa68)
02-19 17:57:44.184 3512 3512 I wrap.sh : #7 0x6fceef74 (/apex/com.android.art/javalib/arm64/boot.oat+0xb2f74)
addr2line定位到native-lib.cpp:83

對應(yīng)代碼如下:

attempting double-free
/*** 測試重復(fù)釋放*/
extern "C" JNIEXPORT void Java_com_nxg_asantest_ASanTestUtil_testRepeatFree(JNIEnv *env, jclass cls) {__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "enter fun %s ...", __FUNCTION__ );int *p = new int[3];delete []p;delete []p;delete []p;delete []p;__android_log_print(ANDROID_LOG_DEBUG, "ASanCrash", "leave fun %s ...", __FUNCTION__ );
}
ASan檢測到了attempting double-free并主動(dòng)的拋出了異常。
02-19 17:57:47.308 3665 3665 I wrap.sh : =================================================================
02-19 17:57:47.309 3665 3665 I wrap.sh : [1m[31m==3685==ERROR: AddressSanitizer: attempting double-free on 0x003d32b6c010 in thread T0 (om.nxg.asantest):
02-19 17:57:47.332 3665 3665 I wrap.sh : [1m[0m #0 0x7c1233dc64 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libclang_rt.asan-aarch64-android.so+0xaac64)
02-19 17:57:47.332 3665 3665 I wrap.sh : #1 0x78e31e8b08 (/data/app/~~O3c2gJpllNHK6xBZIypJyQ==/com.nxg.asantest-iQvQxnZ3heMOyVK67qkkyw==/lib/arm64/libasantest.so+0x3b08)
02-19 17:57:47.332 3665 3665 I wrap.sh : #2 0x7964222244 (/apex/com.android.art/lib64/libart.so+0x222244)
02-19 17:57:47.332 3665 3665 I wrap.sh : #3 0x7964211608 (/apex/com.android.art/lib64/libart.so+0x211608)
02-19 17:57:47.332 3665 3665 I wrap.sh : #4 0x7964218964 (/apex/com.android.art/lib64/libart.so+0x218964)
02-19 17:57:47.332 3665 3665 I wrap.sh : #5 0x7964284208 (/apex/com.android.art/lib64/libart.so+0x284208)
02-19 17:57:47.332 3665 3665 I wrap.sh : #6 0x796461e8f8 (/apex/com.android.art/lib64/libart.so+0x61e8f8)
02-19 17:57:47.332 3665 3665 I wrap.sh : #7 0x796458fa68 (/apex/com.android.art/lib64/libart.so+0x58fa68)
02-19 17:57:47.332 3665 3665 I wrap.sh : #8 0x70f73f74 (/apex/com.android.art/javalib/arm64/boot.oat+0xb2f74)
addr2line定位到native-lib.cpp:94

對應(yīng)代碼如下:

進(jìn)過測試,ASan 確實(shí)檢測以下問題:
堆棧和堆緩沖區(qū)上溢/下溢
釋放之后的堆使用情況
超出范圍的堆棧使用情況
重復(fù)釋放/錯(cuò)誤釋放
但stack-use-after-return沒檢測出來,暫時(shí)不知道咋回事,需要了解的可以看這里:AddressSanitizerExampleUseAfterReturn
關(guān)于內(nèi)存泄露檢測,暫時(shí)還先不管,后面另外寫一篇文章來單獨(dú)講講。
一些注意事項(xiàng)
無法檢測代碼錯(cuò)誤?
可能是編譯器做了優(yōu)化。參考官方WIKI:
Q: Why didn't ASan report an obviously invalid memory access in my code?A1: If your errors is too obvious, compiler might have already optimized it out by the time Asan runs.A2: Another, C-only option is accesses to global common symbols which are not protected by Asan (you can use -fno-common to disable generation of common symbols and hopefully detect more bugs).A3: If _FORTIFY_SOURCE is enabled, ASan may have false positives, see next question.
支持Android O MR1(API 級(jí)別 27)之前的版本
上面提到的wrap.sh腳本只支持Android O MR1(API 級(jí)別 27)及之后的系統(tǒng)版本,針對低版本如Android 5.0,我們可以使用asan_device_setup腳本手動(dòng)安裝ASan到設(shè)備中。
在設(shè)備中安裝Address Sanitizer
準(zhǔn)備工作
● 設(shè)備需要root
● 找到asan_device_setup腳本
關(guān)于asan_device_setup腳本,在Android SDK自帶的ndk中,其腳本路徑為:
/ndk/23.1.7779620/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/12.0.8/bin
注意:不同的NDK版本路徑可能稍微不同

asan_device_setup 使用說明
xiangang@xiangang-ubuntu:~/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/12.0.8/bin$ ./asan_device_setup -h
usage: ./asan_device_setup [--revert] [--device device-id] [--lib path] [--extra-options options]--revert: Uninstall ASan from the device.--lib: Path to ASan runtime library.--extra-options: Extra ASAN_OPTIONS.--device: Install to the given device. Use 'adb devices' to finddevice-id.--use-su: Use 'su -c' prefix for every adb command instead of using'adb root' once.
安裝
執(zhí)行adb devices命令,查看已連接的設(shè)備,確保adb只連接一個(gè)設(shè)備的情況下,通過執(zhí)行./asan_device_setup 命令進(jìn)行安裝。如果adb連接了多個(gè)設(shè)備,就會(huì)報(bào)錯(cuò)error: more than one device/emulator。
如何確保adb只連接一個(gè)設(shè)備?
首先拔掉所有通過USB連接電腦的設(shè)備,再執(zhí)行adb kill-server或者adb disconnect,然后再重新執(zhí)行adb connect 連接目標(biāo)設(shè)備即可。當(dāng)然最好再次執(zhí)行adb devices檢查是否只連接了一個(gè)設(shè)備,最后重新執(zhí)行./asan_device_setup,第一次會(huì)先root設(shè)備,然后再重新執(zhí)行一次./asan_device_setup即可。
當(dāng)然也可以使用--device指定設(shè)備:
--device: Install to the given device. Use 'adb devices' to finddevice-id.
如果設(shè)備無法root,可以嘗試加上--use-su
--use-su: Use 'su -c' prefix for every adb command instead of using'adb root' once.
如果腳本執(zhí)行成功,那么設(shè)備就會(huì)自動(dòng)重啟。示例日志如下:
xiangang@xiangang-ubuntu:/work/android/android-ndk-r20/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/8.0.7/bin$ ls -l
總用量 16
-rwxr-xr-x 1 lbrd lbrd 13721 5月 22 2019 asan_device_setup
xiangang@xiangang-ubuntu:/work/android/android-ndk-r20/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/8.0.7/bin$ adb connect 192.168.1.128:5656
connected to 192.168.1.128:5656
xiangang@xiangang-ubuntu:/work/android/android-ndk-r20/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/8.0.7/bin$ ls
asan_device_setup
xiangang@xiangang-ubuntu:/work/android/android-ndk-r20/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/8.0.7/bin$ ./asan_device_setup
>> Remounting /system rw
restarting adbd as root
error: closed
xiangang@xiangang-ubuntu:/work/android/android-ndk-r20/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/8.0.7/bin$ ./asan_device_setup
>> Remounting /system rw
adbd is already running as root
remount succeeded
Target architecture: arm
>> Copying files from the device
/system/lib/libclang_rt.asan-arm-android.so: 1 file pulled, 0 skipped. 9.6 MB/s (2112004 bytes in 0.209s)
/system/bin/app_process32: 1 file pulled, 0 skipped. 3.6 MB/s (29012 bytes in 0.008s)
adb: error: failed to stat remote object '/system/bin/app_process.wrap': No such file or directory
adb: error: failed to stat remote object '/system/bin/asanwrapper': No such file or directory
>> New installation
>> Generating wrappers
只在 new/ 存在:app_process.wrap
只在 new/ 存在:asanwrapper
文件 old/libclang_rt.asan-arm-android.so 和 new/libclang_rt.asan-arm-android.so 不同
>> Pushing files to the device
Installing /system/lib/libclang_rt.asan-arm-android.so 644
/tmp/tmp.CH44fgn4x2/new/libclang_rt.asan-arm-android.so: 1 file pushed, 0 skipped. 2517.8 MB/s (2110248 bytes in 0.001s)
Installing /system/bin/app_process32 755 u:object_r:zygote_exec:s0
/tmp/tmp.CH44fgn4x2/new/app_process32: 1 file pushed, 0 skipped. 82.7 MB/s (29012 bytes in 0.000s)
Installing /system/bin/app_process.wrap 755 u:object_r:zygote_exec:s0
/tmp/tmp.CH44fgn4x2/new/app_process.wrap: 1 file pushed, 0 skipped. 2.4 MB/s (242 bytes in 0.000s)
Installing /system/bin/asanwrapper 755 u:object_r:zygote_exec:s0
/tmp/tmp.CH44fgn4x2/new/asanwrapper: 1 file pushed, 0 skipped. 0.7 MB/s (67 bytes in 0.000s)
>> Restarting shell (asynchronous)
>> Please wait until the device restarts
xiangang@xiangang-ubuntu:/work/android/android-ndk-r20/toolchains/llvm/prebuilt/linux-x86_64/lib64/clang/8.0.7/bin$
建議看下asan_device_setup腳本是怎么寫的,可以參考自己寫一些有用的測試腳本。
卸載Address Sanitizer
在實(shí)際測試中,發(fā)現(xiàn)安裝了ASan會(huì)導(dǎo)致dumpsys meminfo的數(shù)據(jù)受到影響,從而導(dǎo)致性能監(jiān)控內(nèi)存失效??赡苁且?yàn)锳San的關(guān)系,目前沒有解決辦法,只能卸載ASan了.
執(zhí)行:?./asan_device_setup?--revert?卸載ASan。
更多問題建議仔細(xì)閱讀官方WIKI:AddressSanitizer Github WIKI或搜索issues
Address Sanitizer實(shí)戰(zhàn)
一個(gè)實(shí)際的項(xiàng)目排查過程供大家參考。

SUMMARY: AddressSanitizer: double-free (/system/lib/libclang_rt.asan-arm-android.so+0xafe03)檢測到是double-free,參照前面有問題的代碼寫法,我們很容易排查到問題。但是不會(huì)有有人這樣寫,所以像這種double-free通常都是多線程操作同一個(gè)static變量引起的。
截圖中8314跟8026線程調(diào)用同一個(gè)方法操作static指針獲取了GetByteArrayElements的返回值并且都free了,因?yàn)槭峭粋€(gè)地址,造成double free。8314和8026(single-pool-3-t)線程是Java線程池中的線程,
寫在最后,首先非常感謝您耐心閱讀完整篇文章,堅(jiān)持寫原創(chuàng)且基于實(shí)戰(zhàn)的文章不是件容易的事,如果本文剛好對您有點(diǎn)幫助,歡迎您給文章點(diǎn)贊評(píng)論,您的鼓勵(lì)是筆者堅(jiān)持不懈的動(dòng)力。若文章有不對之處也歡迎指正,再次感謝。
參考資料
Android官方Address Sanitizer入門教程
Google官方AddressSanitizer WIKI