NE abnormal problem

brief introduction

NE, the full name of Native Exception, in Android, mainly refers to exceptions in native programs or natvie libraries running in user space.

NE problems usually lead to program collapse, resulting in unstable functional modules.

Common types of NE problems

The following describes several common Native Crash situations:

  1. Actively throwing an exception, calling abort() in the code, the system sends the signal SIGABRT(6) to the process. This problem is usually implemented by the code to the abnormal branch. It needs to check to see what conditions result, and CamX code is used more.

  2. The process is killed by SIGKILL(9). For example, it is killed by adb shell kill -9 $PID or a process management mechanism. The APP process may encounter this problem and generally does not generate a tombstone file.

  3. Null pointer. In the address space of the process, the permission of the first page starting from 0 is set to be unreadable and writable. When the instruction of the process attempts to access the address in the page (such as reading the memory pointed by the null pointer), the processor will generate an exception, and then the Linux kernel will send a segment error signal SIGSEGV(11) to the process

  4. The wild pointer refers to an invalid address. If the address is unreadable and writable, it will crash immediately (the kernel sends a segment error signal SIGSEGV to the process). At this time, the bug will be found soon.

    If the accessed address is writable and the memory is modified through the wild pointer, it is likely that Crash will occur after a period of time (after other codes use the memory). At this time, the call stack displayed when viewing Crash may not be related to the code part where the wild pointer is located. It is a kind of memory.

  5. Array out of bounds / buffer overflow. The situation is similar to that of a wild pointer. It accesses an invalid address and steps on someone else's memory area.

Common debugging tools

The debugging tool is to help us locate the point where the problem occurs. (I tried, but failed. I prompted that the file format of so is wrong, and the location content should be consistent with that of backtrace.)

Arm linux Android addr2line is a tool provided in NDK to convert memory addresses into line numbers. Generally, the specific point is to locate the specific line in the file according to the offset memory address in various logs, such as so library logs contained in trace logs and tometone logs.

Reference link:

https://blog.csdn.net/yanzheng1113/article/details/8148091

https://blog.csdn.net/tkwxty/article/details/103493624

Relevant instructions:

ubuntu@ubuntu:~$ arm-linux-androideabi-addr2line  --h
Usage: arm-linux-androideabi-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

arm-linux-androideabi-addr2line: supported targets: elf32-littlearm elf32-bigarm elf32-little elf32-big plugin srec symbolsrec verilog tekhex binary ihex
Report bugs to <http://www.sourceware.org/bugzilla/>

We often use:

arm-linux-androideabi-addr2line -e To be debugged so Library path memory address

The addr2line tool is integrated in both NDK and Android source code. Here I take the Android source code as a demonstration. We can find many addr2line files through search. We need to choose the one suitable for ourselves. We use arm linux Android addr2line

find . -name *addr2line*
./kernel-4.19-lc/scripts/faddr2line
./kernel-5.10/scripts/faddr2line
./ccu_tool/md32ccu/ToolChain/install_md32/share/man/man1/md32-elf-addr2line.1
./prebuilts/gcc/darwin-x86/aarch64/aarch64-linux-android-4.9/bin/aarch64-linux-android-addr2line
./prebuilts/gcc/darwin-x86/x86/x86_64-linux-android-4.9/bin/x86_64-linux-android-addr2line
./prebuilts/gcc/darwin-x86/arm/arm-linux-androideabi-4.9/bin/arm-linux-androideabi-addr2line
./prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9/bin/aarch64-linux-android-addr2line
./prebuilts/gcc/linux-x86/aarch64/gcc-arm-8.3-2019.03-x86_64-aarch64-elf/bin/aarch64-elf-addr2line
./prebuilts/gcc/linux-x86/aarch64/gcc-arm-8.3-2019.03-x86_64-aarch64-elf/share/doc/binutils.html/addr2line.html
./prebuilts/gcc/linux-x86/aarch64/gcc-arm-8.3-2019.03-x86_64-aarch64-elf/share/man/man1/aarch64-elf-addr2line.1
./prebuilts/gcc/linux-x86/aarch64/gcc-arm-9.2-2019.12-x86_64-aarch64-none-elf/bin/aarch64-none-elf-addr2line
./prebuilts/gcc/linux-x86/aarch64/gcc-arm-9.2-2019.12-x86_64-aarch64-none-elf/share/doc/binutils.html/addr2line.html
./prebuilts/gcc/linux-x86/aarch64/gcc-arm-9.2-2019.12-x86_64-aarch64-none-elf/share/man/man1/aarch64-none-elf-addr2line.1
./prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9.1/bin/aarch64-linux-android-addr2line
./prebuilts/gcc/linux-x86/x86/x86_64-linux-android-4.9/bin/x86_64-linux-android-addr2line
./prebuilts/gcc/linux-x86/arc/arc_gnu_2016.09_prebuilt_elf32_le_linux/bin/arc-elf32-addr2line
./prebuilts/gcc/linux-x86/arc/arc_gnu_2016.09_prebuilt_elf32_le_linux/share/man/man1/arc-elf32-addr2line.1
./prebuilts/gcc/linux-x86/arm/gcc-arm-none-eabi-4_7-2012q4/bin/arm-none-eabi-addr2line
./prebuilts/gcc/linux-x86/arm/arm-linux-androideabi-4.9.1/bin/arm-linux-androideabi-addr2line
./prebuilts/gcc/linux-x86/arm/gcc-arm-8.3-2019.03-x86_64-arm-eabi/bin/arm-eabi-addr2line
./prebuilts/gcc/linux-x86/arm/gcc-arm-8.3-2019.03-x86_64-arm-eabi/share/doc/binutils.html/addr2line.html
./prebuilts/gcc/linux-x86/arm/gcc-arm-8.3-2019.03-x86_64-arm-eabi/share/man/man1/arm-eabi-addr2line.1
./prebuilts/gcc/linux-x86/arm/gcc-linaro-7.1.1-2017.08-x86_64_arm-eabi/bin/arm-eabi-addr2line
./prebuilts/gcc/linux-x86/arm/gcc-linaro-7.1.1-2017.08-x86_64_arm-eabi/share/doc/binutils.html/addr2line.html
./prebuilts/gcc/linux-x86/arm/gcc-linaro-7.1.1-2017.08-x86_64_arm-eabi/share/man/man1/arm-eabi-addr2line.1
./prebuilts/rust/darwin-x86/1.48.0/lib/rustlib/i686-linux-android/lib/libaddr2line-53d59ae352c562ca.rlib
./prebuilts/rust/darwin-x86/1.49.0/lib/rustlib/x86_64-linux-android/lib/libaddr2line-e67be5e2460aec9d.rlib
...... ......

At the same time, after source build/envsetup.sh and lunch in the Android source code, we enter the following commands and find that Android can supplement them for us:

ubuntu@ubuntu:/mnt/disk2/new$ arm-linux-androideabi-
arm-linux-androideabi-addr2line   arm-linux-androideabi-dwp         arm-linux-androideabi-gcc-ar      arm-linux-androideabi-ld  arm-linux-androideabi-ranlib
arm-linux-androideabi-ar          arm-linux-androideabi-elfedit     arm-linux-androideabi-gcc-nm      arm-linux-androideabi-ld.bfd      arm-linux-androideabi-readelf
arm-linux-androideabi-as          arm-linux-androideabi-g++         arm-linux-androideabi-gcc-ranlib  arm-linux-androideabi-ld.gold     arm-linux-androideabi-size
arm-linux-androideabi-c++         arm-linux-androideabi-gcc         arm-linux-androideabi-gcov        arm-linux-androideabi-nm arm-linux-androideabi-strings
arm-linux-androideabi-c++filt     arm-linux-androideabi-gcc-4.9     arm-linux-androideabi-gcov-tool   arm-linux-androideabi-objcopy     arm-linux-androideabi-strip
arm-linux-androideabi-cpp         arm-linux-androideabi-gcc-4.9.x   arm-linux-androideabi-gprof       arm-linux-androideabi-objdump 

Practical application:

Example from CSDN: https://blog.csdn.net/tkwxty/article/details/103493624

DALVIK THREADS (23):
"main" prio=5 tid=1 Native
  | group="main" sCount=1 dsCount=0 obj=0x73698300 self=0xb73b40f0
  | sysTid=20557 nice=0 cgrp=default sched=0/0 handle=0xb6f15bec
  | state=S schedstat=( 15160273605 193890933 2101 ) utm=1424 stm=92 core=0 HZ=100
  | stack=0xbe2fb000-0xbe2fd000 stackSize=8MB
  | held mutexes=
  kernel: (couldn't read /proc/self/task/20557/stack)
  native: #00 pc 0000f9a8  /system/lib/libc.so (syscall+28)
  native: #01 pc 00013185  /system/lib/libc.so (_Z33__pthread_cond_timedwait_relativeP14pthread_cond_tP15pthread_mutex_tPK8timespec+56)
  native: #02 pc 0003b2e3  /system/lib/libhwui.so (???)
  native: #03 pc 0003b319  /system/lib/libhwui.so (???)
  native: #04 pc 00936c8b  /data/dalvik-cache/arm/system@framework@boot.oat (Java_android_view_ThreadedRenderer_nSyncAndDrawFrame__JJJF+134)

Here we take #03 as an example for analysis. The specific steps are as follows:

(1) Find the libhwui.so file that has not been optimized. Of course, find it, as shown below

xxx$ find .  -name libhwui.so
./out/target/product/msm8909/system/lib/libhwui.so
./out/target/product/msm8909/obj/SHARED_LIBRARIES/libhwui_intermediates/LINKED/libhwui.so
./out/target/product/msm8909/obj/lib/libhwui.so
./out/target/product/msm8909/symbols/system/lib/libhwui.so	//This is what we want to use

(2) Found memory address "0003b319"

(3) Execute command

xxx$ arm-linux-androideabi-addr2line -f -e  ./out/target/product/msm8909/symbols/system/lib/libhwui.so  0003b319
_ZN7android10uirenderer12renderthread13DrawFrameTask9drawFrameExx
xxx/frameworks/base/libs/hwui/renderthread/DrawFrameTask.cpp:77

Case study on Dual Camera switching

Keywords where NE occurs: AEE_AED

09-20 07:37:29.801  5665  5665 I AEE_AED : handle_request(11)
09-20 07:37:29.802  5665  5665 I AEE_AED : pid: 797, tid: 5524, >>> /vendor/bin/hw/camerahalserver <<<

It can be seen that the camerahalserver has an ne. Generally, there is a reproduction problem. If an ne is generated, an exception folder, such as AEE, will be generated in the / data directory of the mobile phone_ Exp folder, which contains some db files, tombstones folder (which will record the type of NE and backtrace:), etc. with the help of debugging tools, we can better locate the problem.

If there is no db folder generation, you can try the following command:

adb root
adb shell setenforce 0
adb shell setprop persist.vendor.mtk.aee.mode 3
adb shell setprop persist.vendor.mtk.aeev.mode 3
adb shell setprop persist.vendor.aeev.core.direct enable            
adb shell setprop persist.vendor.aeev.core.dump enable
adb reboot

Use the command to grab the log and find the following fragments ():

09-24 14:25:23.469 26803 26803 I AEE_AED : pid: 17981, tid: 26672, name: N3DNode  >>> /vendor/bin/hw/camerahalserver <<<
09-24 14:25:23.469 26803 26803 I AEE_AED : signal 11 (SIGSEGV), code --------, fault addr --------

You can see that signal 11 (SIGSEGV): is a null pointer. See the following log (aee_aed: stack start (7abe29b9c0), end (7abe29d963), length (1fa3)):

09-24 14:25:23.448 26803 26803 I AEE_AED : stack start(7abe29b9c0),end(7abe29d963),length(1fa3)
09-24 14:25:23.451 26803 26803 I AEE_AED :  dump_stack64:dump stack ok
09-24 14:25:23.463 26803 26803 I AEE_AED :     #00 pc 000000000004cdf8  /apex/com.android.runtime/lib64/bionic/libc.so (__memcpy+248) (BuildId: e09b24987327c22afce455f46935acc6)
09-24 14:25:23.464 26803 26803 I AEE_AED :     #01 pc 000000000003da40  /vendor/lib64/libfeature.vsdof.hal.so (N3D_HAL_IMP::__saveNVRAM()+160) (BuildId: ed08202e1c646e1e81a271952c52469e)
09-24 14:25:23.464 26803 26803 I AEE_AED :     #02 pc 000000000003d7b0  /vendor/lib64/libfeature.vsdof.hal.so (N3D_HAL_IMP::~N3D_HAL_IMP()+1344) (BuildId: ed08202e1c646e1e81a271952c52469e)
09-24 14:25:23.464 26803 26803 I AEE_AED :     #03 pc 000000000003dc48  /vendor/lib64/libfeature.vsdof.hal.so (N3D_HAL_IMP::~N3D_HAL_IMP()+16) (BuildId: ed08202e1c646e1e81a271952c52469e)
09-24 14:25:23.465 26803 26803 I AEE_AED :     #04 pc 00000000000c3528  /vendor/lib64/libmtkcam.featurepipe.depthmap.so (NSCam::NSCamFeature::NSFeaturePipe_DepthMap::N3DNode::cleanUp()+400) (BuildId: fb069071692db5077ef6e67eb7b312a5)
09-24 14:25:23.465 26803 26803 I AEE_AED :     #05 pc 00000000000c4368  /vendor/lib64/libmtkcam.featurepipe.depthmap.so (NSCam::NSCamFeature::NSFeaturePipe_DepthMap::N3DNode::onThreadStop()+272) (BuildId: fb069071692db5077ef6e67eb7b312a5)
09-24 14:25:23.466 26803 26803 I AEE_AED :     #06 pc 00000000000c449c  /vendor/lib64/libmtkcam.featurepipe.depthmap.so (non-virtual thunk to NSCam::NSCamFeature::NSFeaturePipe_DepthMap::N3DNode::onThreadStop()+12) (BuildId: fb069071692db5077ef6e67eb7b312a5)
09-24 14:25:23.467 26803 26803 I AEE_AED :     #07 pc 00000000001f75a4  /vendor/lib64/libmtkcam.featurepipe.streaming.so (NSCam::NSCamFeature::NSFeaturePipe::CamThread::CamThreadHandle::threadLoop()+180) (BuildId: 5957950dd6e0bad9684a68f0c8002930)
09-24 14:25:23.467 26803 26803 I AEE_AED :     #08 pc 0000000000012304  /apex/com.android.vndk.v31/lib64/libutils.so (android::Thread::_threadLoop(void*)+460) (BuildId: 5f04ee98c91df9e28e69d08a6224093d)
09-24 14:25:23.467 26803 26803 I AEE_AED :     #09 pc 0000000000011acc  /apex/com.android.vndk.v31/lib64/libutils.so thread_data_t::trampoline(thread_data_t const*)+404) (BuildId: 5f04ee98c91df9e28e69d08a6224093d)
09-24 14:25:23.467 26803 26803 I AEE_AED :     #10 pc 00000000000b44e8  /apex/com.android.runtime/lib64/bionic/libc.so (__pthread_start(void*)+264) (BuildId: e09b24987327c22afce455f46935acc6)
09-24 14:25:23.467 26803 26803 I AEE_AED :     #11 pc 0000000000052848  /apex/com.android.runtime/lib64/bionic/libc.so (__start_thread+64) (BuildId: e09b24987327c22afce455f46935acc6)
09-24 14:25:23.467 26803 26803 I AEE_AED : ne_direct_unwind end

Or backtrace

09-24 14:25:23.506 26803 26803 I AEE_AED : backtrace:
09-24 14:25:23.506 26803 26803 I AEE_AED :     #00 pc 000000000004cdf8  /apex/com.android.runtime/lib64/bionic/libc.so (__memcpy+248)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #01 pc 000000000003da40  /vendor/lib64/libfeature.vsdof.hal.so (N3D_HAL_IMP::__saveNVRAM()+160)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #02 pc 000000000003d7b0  /vendor/lib64/libfeature.vsdof.hal.so (N3D_HAL_IMP::~N3D_HAL_IMP()+1344)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #03 pc 000000000003dc48  /vendor/lib64/libfeature.vsdof.hal.so (N3D_HAL_IMP::~N3D_HAL_IMP()+16)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #04 pc 00000000000c3528  /vendor/lib64/libmtkcam.featurepipe.depthmap.so (NSCam::NSCamFeature::NSFeaturePipe_DepthMap::N3DNode::cleanUp()+400)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #05 pc 00000000000c4368  /vendor/lib64/libmtkcam.featurepipe.depthmap.so (NSCam::NSCamFeature::NSFeaturePipe_DepthMap::N3DNode::onThreadStop()+272)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #06 pc 00000000000c449c  /vendor/lib64/libmtkcam.featurepipe.depthmap.so (non-virtual thunk to NSCam::NSCamFeature::NSFeaturePipe_DepthMap::N3DNode::onThreadStop()+12)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #07 pc 00000000001f75a4  /vendor/lib64/libmtkcam.featurepipe.streaming.so (NSCam::NSCamFeature::NSFeaturePipe::CamThread::CamThreadHandle::threadLoop()+180)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #08 pc 0000000000012304  /apex/com.android.vndk.v31/lib64/libutils.so (android::Thread::_threadLoop(void*)+460)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #09 pc 0000000000011acc  /apex/com.android.vndk.v31/lib64/libutils.so (thread_data_t::trampoline(thread_data_t const*)+404)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #10 pc 00000000000b44e8  /apex/com.android.runtime/lib64/bionic/libc.so (__pthread_start(void*)+264)
09-24 14:25:23.506 26803 26803 I AEE_AED :     #11 pc 0000000000052848  /apex/com.android.runtime/lib64/bionic/libc.so (__start_thread+64)

As you can see, yes__ memcpy—>__ saveNVRAM()-—>~N3D_ HAL_ IMP()–>…… ……

Location code:

bool
N3D_HAL_IMP::__saveNVRAM()
{
	...... ......
    ::memcpy(__convAddr, __convergenceData, __CONV_SIZE);//Point of occurrence
    ...... ......
    return bResult;
}
	----->
    N3D_HAL_IMP::~N3D_HAL_IMP()
	{
    	...... ......
    	} else if(__spPreviewKernel == &__n3dKernel) {
        	__spPreviewKernel = NULL;
        	__saveNVRAM();
		...... ......
    	MY_LOGD("%s -", (__eScenario == eSTEREO_SCENARIO_CAPTURE)?"Cap":"PV");
	}
	<-----------------------------------------------

Print the log at memcpy and find__ convAddr is null, check__ The assignment logic of convAddr.

The key is to print out the stack information

Keywords: C++ Android

Added by Leveecius on Wed, 01 Dec 2021 14:24:11 +0200